1 //===------- TreeTransform.h - Semantic Tree Transformation -----*- C++ -*-===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //===----------------------------------------------------------------------===//
8 // This file implements a semantic tree transformation that takes a given
9 // AST and rebuilds it, possibly transforming some nodes in the process.
11 //===----------------------------------------------------------------------===//
13 #ifndef LLVM_CLANG_LIB_SEMA_TREETRANSFORM_H
14 #define LLVM_CLANG_LIB_SEMA_TREETRANSFORM_H
16 #include "CoroutineStmtBuilder.h"
17 #include "TypeLocBuilder.h"
18 #include "clang/AST/Decl.h"
19 #include "clang/AST/DeclObjC.h"
20 #include "clang/AST/DeclTemplate.h"
21 #include "clang/AST/Expr.h"
22 #include "clang/AST/ExprCXX.h"
23 #include "clang/AST/ExprConcepts.h"
24 #include "clang/AST/ExprObjC.h"
25 #include "clang/AST/ExprOpenMP.h"
26 #include "clang/AST/OpenMPClause.h"
27 #include "clang/AST/Stmt.h"
28 #include "clang/AST/StmtCXX.h"
29 #include "clang/AST/StmtObjC.h"
30 #include "clang/AST/StmtOpenACC.h"
31 #include "clang/AST/StmtOpenMP.h"
32 #include "clang/Basic/DiagnosticParse.h"
33 #include "clang/Basic/OpenMPKinds.h"
34 #include "clang/Sema/Designator.h"
35 #include "clang/Sema/EnterExpressionEvaluationContext.h"
36 #include "clang/Sema/Lookup.h"
37 #include "clang/Sema/Ownership.h"
38 #include "clang/Sema/ParsedTemplate.h"
39 #include "clang/Sema/ScopeInfo.h"
40 #include "clang/Sema/SemaDiagnostic.h"
41 #include "clang/Sema/SemaInternal.h"
42 #include "clang/Sema/SemaObjC.h"
43 #include "clang/Sema/SemaOpenACC.h"
44 #include "clang/Sema/SemaOpenMP.h"
45 #include "clang/Sema/SemaPseudoObject.h"
46 #include "clang/Sema/SemaSYCL.h"
47 #include "llvm/ADT/ArrayRef.h"
48 #include "llvm/Support/ErrorHandling.h"
52 using namespace llvm::omp
;
57 /// A semantic tree transformation that allows one to transform one
58 /// abstract syntax tree into another.
60 /// A new tree transformation is defined by creating a new subclass \c X of
61 /// \c TreeTransform<X> and then overriding certain operations to provide
62 /// behavior specific to that transformation. For example, template
63 /// instantiation is implemented as a tree transformation where the
64 /// transformation of TemplateTypeParmType nodes involves substituting the
65 /// template arguments for their corresponding template parameters; a similar
66 /// transformation is performed for non-type template parameters and
67 /// template template parameters.
69 /// This tree-transformation template uses static polymorphism to allow
70 /// subclasses to customize any of its operations. Thus, a subclass can
71 /// override any of the transformation or rebuild operators by providing an
72 /// operation with the same signature as the default implementation. The
73 /// overriding function should not be virtual.
75 /// Semantic tree transformations are split into two stages, either of which
76 /// can be replaced by a subclass. The "transform" step transforms an AST node
77 /// or the parts of an AST node using the various transformation functions,
78 /// then passes the pieces on to the "rebuild" step, which constructs a new AST
79 /// node of the appropriate kind from the pieces. The default transformation
80 /// routines recursively transform the operands to composite AST nodes (e.g.,
81 /// the pointee type of a PointerType node) and, if any of those operand nodes
82 /// were changed by the transformation, invokes the rebuild operation to create
85 /// Subclasses can customize the transformation at various levels. The
86 /// most coarse-grained transformations involve replacing TransformType(),
87 /// TransformExpr(), TransformDecl(), TransformNestedNameSpecifierLoc(),
88 /// TransformTemplateName(), or TransformTemplateArgument() with entirely
89 /// new implementations.
91 /// For more fine-grained transformations, subclasses can replace any of the
92 /// \c TransformXXX functions (where XXX is the name of an AST node, e.g.,
93 /// PointerType, StmtExpr) to alter the transformation. As mentioned previously,
94 /// replacing TransformTemplateTypeParmType() allows template instantiation
95 /// to substitute template arguments for their corresponding template
96 /// parameters. Additionally, subclasses can override the \c RebuildXXX
97 /// functions to control how AST nodes are rebuilt when their operands change.
98 /// By default, \c TreeTransform will invoke semantic analysis to rebuild
99 /// AST nodes. However, certain other tree transformations (e.g, cloning) may
100 /// be able to use more efficient rebuild steps.
102 /// There are a handful of other functions that can be overridden, allowing one
103 /// to avoid traversing nodes that don't need any transformation
104 /// (\c AlreadyTransformed()), force rebuilding AST nodes even when their
105 /// operands have not changed (\c AlwaysRebuild()), and customize the
106 /// default locations and entity names used for type-checking
107 /// (\c getBaseLocation(), \c getBaseEntity()).
108 template<typename Derived
>
109 class TreeTransform
{
110 /// Private RAII object that helps us forget and then re-remember
111 /// the template argument corresponding to a partially-substituted parameter
113 class ForgetPartiallySubstitutedPackRAII
{
115 TemplateArgument Old
;
116 // Set the pack expansion index to -1 to avoid pack substitution and
117 // indicate that parameter packs should be instantiated as themselves.
118 Sema::ArgumentPackSubstitutionIndexRAII ResetPackSubstIndex
;
121 ForgetPartiallySubstitutedPackRAII(Derived
&Self
)
122 : Self(Self
), ResetPackSubstIndex(Self
.getSema(), -1) {
123 Old
= Self
.ForgetPartiallySubstitutedPack();
126 ~ForgetPartiallySubstitutedPackRAII() {
127 Self
.RememberPartiallySubstitutedPack(Old
);
134 /// The set of local declarations that have been transformed, for
135 /// cases where we are forced to build new declarations within the transformer
136 /// rather than in the subclass (e.g., lambda closure types).
137 llvm::DenseMap
<Decl
*, Decl
*> TransformedLocalDecls
;
140 /// Initializes a new tree transformer.
141 TreeTransform(Sema
&SemaRef
) : SemaRef(SemaRef
) { }
143 /// Retrieves a reference to the derived class.
144 Derived
&getDerived() { return static_cast<Derived
&>(*this); }
146 /// Retrieves a reference to the derived class.
147 const Derived
&getDerived() const {
148 return static_cast<const Derived
&>(*this);
151 static inline ExprResult
Owned(Expr
*E
) { return E
; }
152 static inline StmtResult
Owned(Stmt
*S
) { return S
; }
154 /// Retrieves a reference to the semantic analysis object used for
155 /// this tree transform.
156 Sema
&getSema() const { return SemaRef
; }
158 /// Whether the transformation should always rebuild AST nodes, even
159 /// if none of the children have changed.
161 /// Subclasses may override this function to specify when the transformation
162 /// should rebuild all AST nodes.
164 /// We must always rebuild all AST nodes when performing variadic template
165 /// pack expansion, in order to avoid violating the AST invariant that each
166 /// statement node appears at most once in its containing declaration.
167 bool AlwaysRebuild() { return SemaRef
.ArgumentPackSubstitutionIndex
!= -1; }
169 /// Whether the transformation is forming an expression or statement that
170 /// replaces the original. In this case, we'll reuse mangling numbers from
171 /// existing lambdas.
172 bool ReplacingOriginal() { return false; }
174 /// Wether CXXConstructExpr can be skipped when they are implicit.
175 /// They will be reconstructed when used if needed.
176 /// This is useful when the user that cause rebuilding of the
177 /// CXXConstructExpr is outside of the expression at which the TreeTransform
179 bool AllowSkippingCXXConstructExpr() { return true; }
181 /// Returns the location of the entity being transformed, if that
182 /// information was not available elsewhere in the AST.
184 /// By default, returns no source-location information. Subclasses can
185 /// provide an alternative implementation that provides better location
187 SourceLocation
getBaseLocation() { return SourceLocation(); }
189 /// Returns the name of the entity being transformed, if that
190 /// information was not available elsewhere in the AST.
192 /// By default, returns an empty name. Subclasses can provide an alternative
193 /// implementation with a more precise name.
194 DeclarationName
getBaseEntity() { return DeclarationName(); }
196 /// Sets the "base" location and entity when that
197 /// information is known based on another transformation.
199 /// By default, the source location and entity are ignored. Subclasses can
200 /// override this function to provide a customized implementation.
201 void setBase(SourceLocation Loc
, DeclarationName Entity
) { }
203 /// RAII object that temporarily sets the base location and entity
204 /// used for reporting diagnostics in types.
205 class TemporaryBase
{
207 SourceLocation OldLocation
;
208 DeclarationName OldEntity
;
211 TemporaryBase(TreeTransform
&Self
, SourceLocation Location
,
212 DeclarationName Entity
) : Self(Self
) {
213 OldLocation
= Self
.getDerived().getBaseLocation();
214 OldEntity
= Self
.getDerived().getBaseEntity();
216 if (Location
.isValid())
217 Self
.getDerived().setBase(Location
, Entity
);
221 Self
.getDerived().setBase(OldLocation
, OldEntity
);
225 /// Determine whether the given type \p T has already been
228 /// Subclasses can provide an alternative implementation of this routine
229 /// to short-circuit evaluation when it is known that a given type will
230 /// not change. For example, template instantiation need not traverse
231 /// non-dependent types.
232 bool AlreadyTransformed(QualType T
) {
236 /// Transform a template parameter depth level.
238 /// During a transformation that transforms template parameters, this maps
239 /// an old template parameter depth to a new depth.
240 unsigned TransformTemplateDepth(unsigned Depth
) {
244 /// Determine whether the given call argument should be dropped, e.g.,
245 /// because it is a default argument.
247 /// Subclasses can provide an alternative implementation of this routine to
248 /// determine which kinds of call arguments get dropped. By default,
249 /// CXXDefaultArgument nodes are dropped (prior to transformation).
250 bool DropCallArgument(Expr
*E
) {
251 return E
->isDefaultArgument();
254 /// Determine whether we should expand a pack expansion with the
255 /// given set of parameter packs into separate arguments by repeatedly
256 /// transforming the pattern.
258 /// By default, the transformer never tries to expand pack expansions.
259 /// Subclasses can override this routine to provide different behavior.
261 /// \param EllipsisLoc The location of the ellipsis that identifies the
264 /// \param PatternRange The source range that covers the entire pattern of
265 /// the pack expansion.
267 /// \param Unexpanded The set of unexpanded parameter packs within the
270 /// \param ShouldExpand Will be set to \c true if the transformer should
271 /// expand the corresponding pack expansions into separate arguments. When
272 /// set, \c NumExpansions must also be set.
274 /// \param RetainExpansion Whether the caller should add an unexpanded
275 /// pack expansion after all of the expanded arguments. This is used
276 /// when extending explicitly-specified template argument packs per
277 /// C++0x [temp.arg.explicit]p9.
279 /// \param NumExpansions The number of separate arguments that will be in
280 /// the expanded form of the corresponding pack expansion. This is both an
281 /// input and an output parameter, which can be set by the caller if the
282 /// number of expansions is known a priori (e.g., due to a prior substitution)
283 /// and will be set by the callee when the number of expansions is known.
284 /// The callee must set this value when \c ShouldExpand is \c true; it may
285 /// set this value in other cases.
287 /// \returns true if an error occurred (e.g., because the parameter packs
288 /// are to be instantiated with arguments of different lengths), false
289 /// otherwise. If false, \c ShouldExpand (and possibly \c NumExpansions)
291 bool TryExpandParameterPacks(SourceLocation EllipsisLoc
,
292 SourceRange PatternRange
,
293 ArrayRef
<UnexpandedParameterPack
> Unexpanded
,
294 bool &ShouldExpand
, bool &RetainExpansion
,
295 std::optional
<unsigned> &NumExpansions
) {
296 ShouldExpand
= false;
300 /// "Forget" about the partially-substituted pack template argument,
301 /// when performing an instantiation that must preserve the parameter pack
304 /// This routine is meant to be overridden by the template instantiator.
305 TemplateArgument
ForgetPartiallySubstitutedPack() {
306 return TemplateArgument();
309 /// "Remember" the partially-substituted pack template argument
310 /// after performing an instantiation that must preserve the parameter pack
313 /// This routine is meant to be overridden by the template instantiator.
314 void RememberPartiallySubstitutedPack(TemplateArgument Arg
) { }
316 /// Note to the derived class when a function parameter pack is
318 void ExpandingFunctionParameterPack(ParmVarDecl
*Pack
) { }
320 /// Transforms the given type into another type.
322 /// By default, this routine transforms a type by creating a
323 /// TypeSourceInfo for it and delegating to the appropriate
324 /// function. This is expensive, but we don't mind, because
325 /// this method is deprecated anyway; all users should be
326 /// switched to storing TypeSourceInfos.
328 /// \returns the transformed type.
329 QualType
TransformType(QualType T
);
331 /// Transforms the given type-with-location into a new
332 /// type-with-location.
334 /// By default, this routine transforms a type by delegating to the
335 /// appropriate TransformXXXType to build a new type. Subclasses
336 /// may override this function (to take over all type
337 /// transformations) or some set of the TransformXXXType functions
338 /// to alter the transformation.
339 TypeSourceInfo
*TransformType(TypeSourceInfo
*DI
);
341 /// Transform the given type-with-location into a new
342 /// type, collecting location information in the given builder
345 QualType
TransformType(TypeLocBuilder
&TLB
, TypeLoc TL
);
347 /// Transform a type that is permitted to produce a
348 /// DeducedTemplateSpecializationType.
350 /// This is used in the (relatively rare) contexts where it is acceptable
351 /// for transformation to produce a class template type with deduced
352 /// template arguments.
354 QualType
TransformTypeWithDeducedTST(QualType T
);
355 TypeSourceInfo
*TransformTypeWithDeducedTST(TypeSourceInfo
*DI
);
358 /// The reason why the value of a statement is not discarded, if any.
359 enum StmtDiscardKind
{
365 /// Transform the given statement.
367 /// By default, this routine transforms a statement by delegating to the
368 /// appropriate TransformXXXStmt function to transform a specific kind of
369 /// statement or the TransformExpr() function to transform an expression.
370 /// Subclasses may override this function to transform statements using some
373 /// \returns the transformed statement.
374 StmtResult
TransformStmt(Stmt
*S
, StmtDiscardKind SDK
= SDK_Discarded
);
376 /// Transform the given statement.
378 /// By default, this routine transforms a statement by delegating to the
379 /// appropriate TransformOMPXXXClause function to transform a specific kind
380 /// of clause. Subclasses may override this function to transform statements
381 /// using some other mechanism.
383 /// \returns the transformed OpenMP clause.
384 OMPClause
*TransformOMPClause(OMPClause
*S
);
386 /// Transform the given attribute.
388 /// By default, this routine transforms a statement by delegating to the
389 /// appropriate TransformXXXAttr function to transform a specific kind
390 /// of attribute. Subclasses may override this function to transform
391 /// attributed statements/types using some other mechanism.
393 /// \returns the transformed attribute
394 const Attr
*TransformAttr(const Attr
*S
);
396 // Transform the given statement attribute.
398 // Delegates to the appropriate TransformXXXAttr function to transform a
399 // specific kind of statement attribute. Unlike the non-statement taking
400 // version of this, this implements all attributes, not just pragmas.
401 const Attr
*TransformStmtAttr(const Stmt
*OrigS
, const Stmt
*InstS
,
404 // Transform the specified attribute.
406 // Subclasses should override the transformation of attributes with a pragma
407 // spelling to transform expressions stored within the attribute.
409 // \returns the transformed attribute.
411 const X##Attr *Transform##X##Attr(const X##Attr *R) { return R; }
412 #include "clang/Basic/AttrList.inc"
414 // Transform the specified attribute.
416 // Subclasses should override the transformation of attributes to do
417 // transformation and checking of statement attributes. By default, this
418 // delegates to the non-statement taking version.
420 // \returns the transformed attribute.
422 const X##Attr *TransformStmt##X##Attr(const Stmt *, const Stmt *, \
423 const X##Attr *A) { \
424 return getDerived().Transform##X##Attr(A); \
426 #include "clang/Basic/AttrList.inc"
428 /// Transform the given expression.
430 /// By default, this routine transforms an expression by delegating to the
431 /// appropriate TransformXXXExpr function to build a new expression.
432 /// Subclasses may override this function to transform expressions using some
435 /// \returns the transformed expression.
436 ExprResult
TransformExpr(Expr
*E
);
438 /// Transform the given initializer.
440 /// By default, this routine transforms an initializer by stripping off the
441 /// semantic nodes added by initialization, then passing the result to
442 /// TransformExpr or TransformExprs.
444 /// \returns the transformed initializer.
445 ExprResult
TransformInitializer(Expr
*Init
, bool NotCopyInit
);
447 /// Transform the given list of expressions.
449 /// This routine transforms a list of expressions by invoking
450 /// \c TransformExpr() for each subexpression. However, it also provides
451 /// support for variadic templates by expanding any pack expansions (if the
452 /// derived class permits such expansion) along the way. When pack expansions
453 /// are present, the number of outputs may not equal the number of inputs.
455 /// \param Inputs The set of expressions to be transformed.
457 /// \param NumInputs The number of expressions in \c Inputs.
459 /// \param IsCall If \c true, then this transform is being performed on
460 /// function-call arguments, and any arguments that should be dropped, will
463 /// \param Outputs The transformed input expressions will be added to this
466 /// \param ArgChanged If non-NULL, will be set \c true if any argument changed
467 /// due to transformation.
469 /// \returns true if an error occurred, false otherwise.
470 bool TransformExprs(Expr
*const *Inputs
, unsigned NumInputs
, bool IsCall
,
471 SmallVectorImpl
<Expr
*> &Outputs
,
472 bool *ArgChanged
= nullptr);
474 /// Transform the given declaration, which is referenced from a type
477 /// By default, acts as the identity function on declarations, unless the
478 /// transformer has had to transform the declaration itself. Subclasses
479 /// may override this function to provide alternate behavior.
480 Decl
*TransformDecl(SourceLocation Loc
, Decl
*D
) {
481 llvm::DenseMap
<Decl
*, Decl
*>::iterator Known
482 = TransformedLocalDecls
.find(D
);
483 if (Known
!= TransformedLocalDecls
.end())
484 return Known
->second
;
489 /// Transform the specified condition.
491 /// By default, this transforms the variable and expression and rebuilds
493 Sema::ConditionResult
TransformCondition(SourceLocation Loc
, VarDecl
*Var
,
495 Sema::ConditionKind Kind
);
497 /// Transform the attributes associated with the given declaration and
498 /// place them on the new declaration.
500 /// By default, this operation does nothing. Subclasses may override this
501 /// behavior to transform attributes.
502 void transformAttrs(Decl
*Old
, Decl
*New
) { }
504 /// Note that a local declaration has been transformed by this
507 /// Local declarations are typically transformed via a call to
508 /// TransformDefinition. However, in some cases (e.g., lambda expressions),
509 /// the transformer itself has to transform the declarations. This routine
510 /// can be overridden by a subclass that keeps track of such mappings.
511 void transformedLocalDecl(Decl
*Old
, ArrayRef
<Decl
*> New
) {
512 assert(New
.size() == 1 &&
513 "must override transformedLocalDecl if performing pack expansion");
514 TransformedLocalDecls
[Old
] = New
.front();
517 /// Transform the definition of the given declaration.
519 /// By default, invokes TransformDecl() to transform the declaration.
520 /// Subclasses may override this function to provide alternate behavior.
521 Decl
*TransformDefinition(SourceLocation Loc
, Decl
*D
) {
522 return getDerived().TransformDecl(Loc
, D
);
525 /// Transform the given declaration, which was the first part of a
526 /// nested-name-specifier in a member access expression.
528 /// This specific declaration transformation only applies to the first
529 /// identifier in a nested-name-specifier of a member access expression, e.g.,
530 /// the \c T in \c x->T::member
532 /// By default, invokes TransformDecl() to transform the declaration.
533 /// Subclasses may override this function to provide alternate behavior.
534 NamedDecl
*TransformFirstQualifierInScope(NamedDecl
*D
, SourceLocation Loc
) {
535 return cast_or_null
<NamedDecl
>(getDerived().TransformDecl(Loc
, D
));
538 /// Transform the set of declarations in an OverloadExpr.
539 bool TransformOverloadExprDecls(OverloadExpr
*Old
, bool RequiresADL
,
542 /// Transform the given nested-name-specifier with source-location
545 /// By default, transforms all of the types and declarations within the
546 /// nested-name-specifier. Subclasses may override this function to provide
547 /// alternate behavior.
548 NestedNameSpecifierLoc
549 TransformNestedNameSpecifierLoc(NestedNameSpecifierLoc NNS
,
550 QualType ObjectType
= QualType(),
551 NamedDecl
*FirstQualifierInScope
= nullptr);
553 /// Transform the given declaration name.
555 /// By default, transforms the types of conversion function, constructor,
556 /// and destructor names and then (if needed) rebuilds the declaration name.
557 /// Identifiers and selectors are returned unmodified. Subclasses may
558 /// override this function to provide alternate behavior.
560 TransformDeclarationNameInfo(const DeclarationNameInfo
&NameInfo
);
562 bool TransformRequiresExprRequirements(
563 ArrayRef
<concepts::Requirement
*> Reqs
,
564 llvm::SmallVectorImpl
<concepts::Requirement
*> &Transformed
);
565 concepts::TypeRequirement
*
566 TransformTypeRequirement(concepts::TypeRequirement
*Req
);
567 concepts::ExprRequirement
*
568 TransformExprRequirement(concepts::ExprRequirement
*Req
);
569 concepts::NestedRequirement
*
570 TransformNestedRequirement(concepts::NestedRequirement
*Req
);
572 /// Transform the given template name.
574 /// \param SS The nested-name-specifier that qualifies the template
575 /// name. This nested-name-specifier must already have been transformed.
577 /// \param Name The template name to transform.
579 /// \param NameLoc The source location of the template name.
581 /// \param ObjectType If we're translating a template name within a member
582 /// access expression, this is the type of the object whose member template
583 /// is being referenced.
585 /// \param FirstQualifierInScope If the first part of a nested-name-specifier
586 /// also refers to a name within the current (lexical) scope, this is the
587 /// declaration it refers to.
589 /// By default, transforms the template name by transforming the declarations
590 /// and nested-name-specifiers that occur within the template name.
591 /// Subclasses may override this function to provide alternate behavior.
593 TransformTemplateName(CXXScopeSpec
&SS
, TemplateName Name
,
594 SourceLocation NameLoc
,
595 QualType ObjectType
= QualType(),
596 NamedDecl
*FirstQualifierInScope
= nullptr,
597 bool AllowInjectedClassName
= false);
599 /// Transform the given template argument.
601 /// By default, this operation transforms the type, expression, or
602 /// declaration stored within the template argument and constructs a
603 /// new template argument from the transformed result. Subclasses may
604 /// override this function to provide alternate behavior.
606 /// Returns true if there was an error.
607 bool TransformTemplateArgument(const TemplateArgumentLoc
&Input
,
608 TemplateArgumentLoc
&Output
,
609 bool Uneval
= false);
611 /// Transform the given set of template arguments.
613 /// By default, this operation transforms all of the template arguments
614 /// in the input set using \c TransformTemplateArgument(), and appends
615 /// the transformed arguments to the output list.
617 /// Note that this overload of \c TransformTemplateArguments() is merely
618 /// a convenience function. Subclasses that wish to override this behavior
619 /// should override the iterator-based member template version.
621 /// \param Inputs The set of template arguments to be transformed.
623 /// \param NumInputs The number of template arguments in \p Inputs.
625 /// \param Outputs The set of transformed template arguments output by this
628 /// Returns true if an error occurred.
629 bool TransformTemplateArguments(const TemplateArgumentLoc
*Inputs
,
631 TemplateArgumentListInfo
&Outputs
,
632 bool Uneval
= false) {
633 return TransformTemplateArguments(Inputs
, Inputs
+ NumInputs
, Outputs
,
637 /// Transform the given set of template arguments.
639 /// By default, this operation transforms all of the template arguments
640 /// in the input set using \c TransformTemplateArgument(), and appends
641 /// the transformed arguments to the output list.
643 /// \param First An iterator to the first template argument.
645 /// \param Last An iterator one step past the last template argument.
647 /// \param Outputs The set of transformed template arguments output by this
650 /// Returns true if an error occurred.
651 template<typename InputIterator
>
652 bool TransformTemplateArguments(InputIterator First
,
654 TemplateArgumentListInfo
&Outputs
,
655 bool Uneval
= false);
657 /// Fakes up a TemplateArgumentLoc for a given TemplateArgument.
658 void InventTemplateArgumentLoc(const TemplateArgument
&Arg
,
659 TemplateArgumentLoc
&ArgLoc
);
661 /// Fakes up a TypeSourceInfo for a type.
662 TypeSourceInfo
*InventTypeSourceInfo(QualType T
) {
663 return SemaRef
.Context
.getTrivialTypeSourceInfo(T
,
664 getDerived().getBaseLocation());
667 #define ABSTRACT_TYPELOC(CLASS, PARENT)
668 #define TYPELOC(CLASS, PARENT) \
669 QualType Transform##CLASS##Type(TypeLocBuilder &TLB, CLASS##TypeLoc T);
670 #include "clang/AST/TypeLocNodes.def"
672 QualType
TransformTemplateTypeParmType(TypeLocBuilder
&TLB
,
673 TemplateTypeParmTypeLoc TL
,
674 bool SuppressObjCLifetime
);
676 TransformSubstTemplateTypeParmPackType(TypeLocBuilder
&TLB
,
677 SubstTemplateTypeParmPackTypeLoc TL
,
678 bool SuppressObjCLifetime
);
680 template<typename Fn
>
681 QualType
TransformFunctionProtoType(TypeLocBuilder
&TLB
,
682 FunctionProtoTypeLoc TL
,
683 CXXRecordDecl
*ThisContext
,
684 Qualifiers ThisTypeQuals
,
685 Fn TransformExceptionSpec
);
687 bool TransformExceptionSpec(SourceLocation Loc
,
688 FunctionProtoType::ExceptionSpecInfo
&ESI
,
689 SmallVectorImpl
<QualType
> &Exceptions
,
692 StmtResult
TransformSEHHandler(Stmt
*Handler
);
695 TransformTemplateSpecializationType(TypeLocBuilder
&TLB
,
696 TemplateSpecializationTypeLoc TL
,
697 TemplateName Template
);
700 TransformDependentTemplateSpecializationType(TypeLocBuilder
&TLB
,
701 DependentTemplateSpecializationTypeLoc TL
,
702 TemplateName Template
,
705 QualType
TransformDependentTemplateSpecializationType(
706 TypeLocBuilder
&TLB
, DependentTemplateSpecializationTypeLoc TL
,
707 NestedNameSpecifierLoc QualifierLoc
);
709 /// Transforms the parameters of a function type into the
712 /// The result vectors should be kept in sync; null entries in the
713 /// variables vector are acceptable.
715 /// LastParamTransformed, if non-null, will be set to the index of the last
716 /// parameter on which transfromation was started. In the event of an error,
717 /// this will contain the parameter which failed to instantiate.
719 /// Return true on error.
720 bool TransformFunctionTypeParams(
721 SourceLocation Loc
, ArrayRef
<ParmVarDecl
*> Params
,
722 const QualType
*ParamTypes
,
723 const FunctionProtoType::ExtParameterInfo
*ParamInfos
,
724 SmallVectorImpl
<QualType
> &PTypes
, SmallVectorImpl
<ParmVarDecl
*> *PVars
,
725 Sema::ExtParameterInfoBuilder
&PInfos
, unsigned *LastParamTransformed
);
727 bool TransformFunctionTypeParams(
728 SourceLocation Loc
, ArrayRef
<ParmVarDecl
*> Params
,
729 const QualType
*ParamTypes
,
730 const FunctionProtoType::ExtParameterInfo
*ParamInfos
,
731 SmallVectorImpl
<QualType
> &PTypes
, SmallVectorImpl
<ParmVarDecl
*> *PVars
,
732 Sema::ExtParameterInfoBuilder
&PInfos
) {
733 return getDerived().TransformFunctionTypeParams(
734 Loc
, Params
, ParamTypes
, ParamInfos
, PTypes
, PVars
, PInfos
, nullptr);
737 /// Transforms the parameters of a requires expresison into the given vectors.
739 /// The result vectors should be kept in sync; null entries in the
740 /// variables vector are acceptable.
742 /// Returns an unset ExprResult on success. Returns an ExprResult the 'not
743 /// satisfied' RequiresExpr if subsitution failed, OR an ExprError, both of
744 /// which are cases where transformation shouldn't continue.
745 ExprResult
TransformRequiresTypeParams(
746 SourceLocation KWLoc
, SourceLocation RBraceLoc
, const RequiresExpr
*RE
,
747 RequiresExprBodyDecl
*Body
, ArrayRef
<ParmVarDecl
*> Params
,
748 SmallVectorImpl
<QualType
> &PTypes
,
749 SmallVectorImpl
<ParmVarDecl
*> &TransParams
,
750 Sema::ExtParameterInfoBuilder
&PInfos
) {
751 if (getDerived().TransformFunctionTypeParams(
752 KWLoc
, Params
, /*ParamTypes=*/nullptr,
753 /*ParamInfos=*/nullptr, PTypes
, &TransParams
, PInfos
))
759 /// Transforms a single function-type parameter. Return null
762 /// \param indexAdjustment - A number to add to the parameter's
763 /// scope index; can be negative
764 ParmVarDecl
*TransformFunctionTypeParam(ParmVarDecl
*OldParm
,
766 std::optional
<unsigned> NumExpansions
,
767 bool ExpectParameterPack
);
769 /// Transform the body of a lambda-expression.
770 StmtResult
TransformLambdaBody(LambdaExpr
*E
, Stmt
*Body
);
771 /// Alternative implementation of TransformLambdaBody that skips transforming
773 StmtResult
SkipLambdaBody(LambdaExpr
*E
, Stmt
*Body
);
775 CXXRecordDecl::LambdaDependencyKind
776 ComputeLambdaDependency(LambdaScopeInfo
*LSI
) {
777 return static_cast<CXXRecordDecl::LambdaDependencyKind
>(
778 LSI
->Lambda
->getLambdaDependencyKind());
781 QualType
TransformReferenceType(TypeLocBuilder
&TLB
, ReferenceTypeLoc TL
);
783 StmtResult
TransformCompoundStmt(CompoundStmt
*S
, bool IsStmtExpr
);
784 ExprResult
TransformCXXNamedCastExpr(CXXNamedCastExpr
*E
);
786 TemplateParameterList
*TransformTemplateParameterList(
787 TemplateParameterList
*TPL
) {
791 ExprResult
TransformAddressOfOperand(Expr
*E
);
793 ExprResult
TransformDependentScopeDeclRefExpr(DependentScopeDeclRefExpr
*E
,
794 bool IsAddressOfOperand
,
795 TypeSourceInfo
**RecoveryTSI
);
797 ExprResult
TransformParenDependentScopeDeclRefExpr(
798 ParenExpr
*PE
, DependentScopeDeclRefExpr
*DRE
, bool IsAddressOfOperand
,
799 TypeSourceInfo
**RecoveryTSI
);
801 ExprResult
TransformUnresolvedLookupExpr(UnresolvedLookupExpr
*E
,
802 bool IsAddressOfOperand
);
804 StmtResult
TransformOMPExecutableDirective(OMPExecutableDirective
*S
);
806 StmtResult
TransformOMPInformationalDirective(OMPExecutableDirective
*S
);
808 // FIXME: We use LLVM_ATTRIBUTE_NOINLINE because inlining causes a ridiculous
809 // amount of stack usage with clang.
810 #define STMT(Node, Parent) \
811 LLVM_ATTRIBUTE_NOINLINE \
812 StmtResult Transform##Node(Node *S);
813 #define VALUESTMT(Node, Parent) \
814 LLVM_ATTRIBUTE_NOINLINE \
815 StmtResult Transform##Node(Node *S, StmtDiscardKind SDK);
816 #define EXPR(Node, Parent) \
817 LLVM_ATTRIBUTE_NOINLINE \
818 ExprResult Transform##Node(Node *E);
819 #define ABSTRACT_STMT(Stmt)
820 #include "clang/AST/StmtNodes.inc"
822 #define GEN_CLANG_CLAUSE_CLASS
823 #define CLAUSE_CLASS(Enum, Str, Class) \
824 LLVM_ATTRIBUTE_NOINLINE \
825 OMPClause *Transform##Class(Class *S);
826 #include "llvm/Frontend/OpenMP/OMP.inc"
828 /// Build a new qualified type given its unqualified type and type location.
830 /// By default, this routine adds type qualifiers only to types that can
831 /// have qualifiers, and silently suppresses those qualifiers that are not
832 /// permitted. Subclasses may override this routine to provide different
834 QualType
RebuildQualifiedType(QualType T
, QualifiedTypeLoc TL
);
836 /// Build a new pointer type given its pointee type.
838 /// By default, performs semantic analysis when building the pointer type.
839 /// Subclasses may override this routine to provide different behavior.
840 QualType
RebuildPointerType(QualType PointeeType
, SourceLocation Sigil
);
842 /// Build a new block pointer type given its pointee type.
844 /// By default, performs semantic analysis when building the block pointer
845 /// type. Subclasses may override this routine to provide different behavior.
846 QualType
RebuildBlockPointerType(QualType PointeeType
, SourceLocation Sigil
);
848 /// Build a new reference type given the type it references.
850 /// By default, performs semantic analysis when building the
851 /// reference type. Subclasses may override this routine to provide
852 /// different behavior.
854 /// \param LValue whether the type was written with an lvalue sigil
855 /// or an rvalue sigil.
856 QualType
RebuildReferenceType(QualType ReferentType
,
858 SourceLocation Sigil
);
860 /// Build a new member pointer type given the pointee type and the
861 /// class type it refers into.
863 /// By default, performs semantic analysis when building the member pointer
864 /// type. Subclasses may override this routine to provide different behavior.
865 QualType
RebuildMemberPointerType(QualType PointeeType
, QualType ClassType
,
866 SourceLocation Sigil
);
868 QualType
RebuildObjCTypeParamType(const ObjCTypeParamDecl
*Decl
,
869 SourceLocation ProtocolLAngleLoc
,
870 ArrayRef
<ObjCProtocolDecl
*> Protocols
,
871 ArrayRef
<SourceLocation
> ProtocolLocs
,
872 SourceLocation ProtocolRAngleLoc
);
874 /// Build an Objective-C object type.
876 /// By default, performs semantic analysis when building the object type.
877 /// Subclasses may override this routine to provide different behavior.
878 QualType
RebuildObjCObjectType(QualType BaseType
,
880 SourceLocation TypeArgsLAngleLoc
,
881 ArrayRef
<TypeSourceInfo
*> TypeArgs
,
882 SourceLocation TypeArgsRAngleLoc
,
883 SourceLocation ProtocolLAngleLoc
,
884 ArrayRef
<ObjCProtocolDecl
*> Protocols
,
885 ArrayRef
<SourceLocation
> ProtocolLocs
,
886 SourceLocation ProtocolRAngleLoc
);
888 /// Build a new Objective-C object pointer type given the pointee type.
890 /// By default, directly builds the pointer type, with no additional semantic
892 QualType
RebuildObjCObjectPointerType(QualType PointeeType
,
893 SourceLocation Star
);
895 /// Build a new array type given the element type, size
896 /// modifier, size of the array (if known), size expression, and index type
899 /// By default, performs semantic analysis when building the array type.
900 /// Subclasses may override this routine to provide different behavior.
901 /// Also by default, all of the other Rebuild*Array
902 QualType
RebuildArrayType(QualType ElementType
, ArraySizeModifier SizeMod
,
903 const llvm::APInt
*Size
, Expr
*SizeExpr
,
904 unsigned IndexTypeQuals
, SourceRange BracketsRange
);
906 /// Build a new constant array type given the element type, size
907 /// modifier, (known) size of the array, and index type qualifiers.
909 /// By default, performs semantic analysis when building the array type.
910 /// Subclasses may override this routine to provide different behavior.
911 QualType
RebuildConstantArrayType(QualType ElementType
,
912 ArraySizeModifier SizeMod
,
913 const llvm::APInt
&Size
, Expr
*SizeExpr
,
914 unsigned IndexTypeQuals
,
915 SourceRange BracketsRange
);
917 /// Build a new incomplete array type given the element type, size
918 /// modifier, and index type qualifiers.
920 /// By default, performs semantic analysis when building the array type.
921 /// Subclasses may override this routine to provide different behavior.
922 QualType
RebuildIncompleteArrayType(QualType ElementType
,
923 ArraySizeModifier SizeMod
,
924 unsigned IndexTypeQuals
,
925 SourceRange BracketsRange
);
927 /// Build a new variable-length array type given the element type,
928 /// size modifier, size expression, and index type qualifiers.
930 /// By default, performs semantic analysis when building the array type.
931 /// Subclasses may override this routine to provide different behavior.
932 QualType
RebuildVariableArrayType(QualType ElementType
,
933 ArraySizeModifier SizeMod
, Expr
*SizeExpr
,
934 unsigned IndexTypeQuals
,
935 SourceRange BracketsRange
);
937 /// Build a new dependent-sized array type given the element type,
938 /// size modifier, size expression, and index type qualifiers.
940 /// By default, performs semantic analysis when building the array type.
941 /// Subclasses may override this routine to provide different behavior.
942 QualType
RebuildDependentSizedArrayType(QualType ElementType
,
943 ArraySizeModifier SizeMod
,
945 unsigned IndexTypeQuals
,
946 SourceRange BracketsRange
);
948 /// Build a new vector type given the element type and
949 /// number of elements.
951 /// By default, performs semantic analysis when building the vector type.
952 /// Subclasses may override this routine to provide different behavior.
953 QualType
RebuildVectorType(QualType ElementType
, unsigned NumElements
,
956 /// Build a new potentially dependently-sized extended vector type
957 /// given the element type and number of elements.
959 /// By default, performs semantic analysis when building the vector type.
960 /// Subclasses may override this routine to provide different behavior.
961 QualType
RebuildDependentVectorType(QualType ElementType
, Expr
*SizeExpr
,
962 SourceLocation AttributeLoc
, VectorKind
);
964 /// Build a new extended vector type given the element type and
965 /// number of elements.
967 /// By default, performs semantic analysis when building the vector type.
968 /// Subclasses may override this routine to provide different behavior.
969 QualType
RebuildExtVectorType(QualType ElementType
, unsigned NumElements
,
970 SourceLocation AttributeLoc
);
972 /// Build a new potentially dependently-sized extended vector type
973 /// given the element type and number of elements.
975 /// By default, performs semantic analysis when building the vector type.
976 /// Subclasses may override this routine to provide different behavior.
977 QualType
RebuildDependentSizedExtVectorType(QualType ElementType
,
979 SourceLocation AttributeLoc
);
981 /// Build a new matrix type given the element type and dimensions.
982 QualType
RebuildConstantMatrixType(QualType ElementType
, unsigned NumRows
,
983 unsigned NumColumns
);
985 /// Build a new matrix type given the type and dependently-defined
987 QualType
RebuildDependentSizedMatrixType(QualType ElementType
, Expr
*RowExpr
,
989 SourceLocation AttributeLoc
);
991 /// Build a new DependentAddressSpaceType or return the pointee
992 /// type variable with the correct address space (retrieved from
993 /// AddrSpaceExpr) applied to it. The former will be returned in cases
994 /// where the address space remains dependent.
996 /// By default, performs semantic analysis when building the type with address
997 /// space applied. Subclasses may override this routine to provide different
999 QualType
RebuildDependentAddressSpaceType(QualType PointeeType
,
1000 Expr
*AddrSpaceExpr
,
1001 SourceLocation AttributeLoc
);
1003 /// Build a new function type.
1005 /// By default, performs semantic analysis when building the function type.
1006 /// Subclasses may override this routine to provide different behavior.
1007 QualType
RebuildFunctionProtoType(QualType T
,
1008 MutableArrayRef
<QualType
> ParamTypes
,
1009 const FunctionProtoType::ExtProtoInfo
&EPI
);
1011 /// Build a new unprototyped function type.
1012 QualType
RebuildFunctionNoProtoType(QualType ResultType
);
1014 /// Rebuild an unresolved typename type, given the decl that
1015 /// the UnresolvedUsingTypenameDecl was transformed to.
1016 QualType
RebuildUnresolvedUsingType(SourceLocation NameLoc
, Decl
*D
);
1018 /// Build a new type found via an alias.
1019 QualType
RebuildUsingType(UsingShadowDecl
*Found
, QualType Underlying
) {
1020 return SemaRef
.Context
.getUsingType(Found
, Underlying
);
1023 /// Build a new typedef type.
1024 QualType
RebuildTypedefType(TypedefNameDecl
*Typedef
) {
1025 return SemaRef
.Context
.getTypeDeclType(Typedef
);
1028 /// Build a new MacroDefined type.
1029 QualType
RebuildMacroQualifiedType(QualType T
,
1030 const IdentifierInfo
*MacroII
) {
1031 return SemaRef
.Context
.getMacroQualifiedType(T
, MacroII
);
1034 /// Build a new class/struct/union type.
1035 QualType
RebuildRecordType(RecordDecl
*Record
) {
1036 return SemaRef
.Context
.getTypeDeclType(Record
);
1039 /// Build a new Enum type.
1040 QualType
RebuildEnumType(EnumDecl
*Enum
) {
1041 return SemaRef
.Context
.getTypeDeclType(Enum
);
1044 /// Build a new typeof(expr) type.
1046 /// By default, performs semantic analysis when building the typeof type.
1047 /// Subclasses may override this routine to provide different behavior.
1048 QualType
RebuildTypeOfExprType(Expr
*Underlying
, SourceLocation Loc
,
1051 /// Build a new typeof(type) type.
1053 /// By default, builds a new TypeOfType with the given underlying type.
1054 QualType
RebuildTypeOfType(QualType Underlying
, TypeOfKind Kind
);
1056 /// Build a new unary transform type.
1057 QualType
RebuildUnaryTransformType(QualType BaseType
,
1058 UnaryTransformType::UTTKind UKind
,
1059 SourceLocation Loc
);
1061 /// Build a new C++11 decltype type.
1063 /// By default, performs semantic analysis when building the decltype type.
1064 /// Subclasses may override this routine to provide different behavior.
1065 QualType
RebuildDecltypeType(Expr
*Underlying
, SourceLocation Loc
);
1067 QualType
RebuildPackIndexingType(QualType Pattern
, Expr
*IndexExpr
,
1069 SourceLocation EllipsisLoc
,
1070 bool FullySubstituted
,
1071 ArrayRef
<QualType
> Expansions
= {});
1073 /// Build a new C++11 auto type.
1075 /// By default, builds a new AutoType with the given deduced type.
1076 QualType
RebuildAutoType(QualType Deduced
, AutoTypeKeyword Keyword
,
1077 ConceptDecl
*TypeConstraintConcept
,
1078 ArrayRef
<TemplateArgument
> TypeConstraintArgs
) {
1079 // Note, IsDependent is always false here: we implicitly convert an 'auto'
1080 // which has been deduced to a dependent type into an undeduced 'auto', so
1081 // that we'll retry deduction after the transformation.
1082 return SemaRef
.Context
.getAutoType(Deduced
, Keyword
,
1083 /*IsDependent*/ false, /*IsPack=*/false,
1084 TypeConstraintConcept
,
1085 TypeConstraintArgs
);
1088 /// By default, builds a new DeducedTemplateSpecializationType with the given
1090 QualType
RebuildDeducedTemplateSpecializationType(TemplateName Template
,
1092 return SemaRef
.Context
.getDeducedTemplateSpecializationType(
1093 Template
, Deduced
, /*IsDependent*/ false);
1096 /// Build a new template specialization type.
1098 /// By default, performs semantic analysis when building the template
1099 /// specialization type. Subclasses may override this routine to provide
1100 /// different behavior.
1101 QualType
RebuildTemplateSpecializationType(TemplateName Template
,
1102 SourceLocation TemplateLoc
,
1103 TemplateArgumentListInfo
&Args
);
1105 /// Build a new parenthesized type.
1107 /// By default, builds a new ParenType type from the inner type.
1108 /// Subclasses may override this routine to provide different behavior.
1109 QualType
RebuildParenType(QualType InnerType
) {
1110 return SemaRef
.BuildParenType(InnerType
);
1113 /// Build a new qualified name type.
1115 /// By default, builds a new ElaboratedType type from the keyword,
1116 /// the nested-name-specifier and the named type.
1117 /// Subclasses may override this routine to provide different behavior.
1118 QualType
RebuildElaboratedType(SourceLocation KeywordLoc
,
1119 ElaboratedTypeKeyword Keyword
,
1120 NestedNameSpecifierLoc QualifierLoc
,
1122 return SemaRef
.Context
.getElaboratedType(Keyword
,
1123 QualifierLoc
.getNestedNameSpecifier(),
1127 /// Build a new typename type that refers to a template-id.
1129 /// By default, builds a new DependentNameType type from the
1130 /// nested-name-specifier and the given type. Subclasses may override
1131 /// this routine to provide different behavior.
1132 QualType
RebuildDependentTemplateSpecializationType(
1133 ElaboratedTypeKeyword Keyword
,
1134 NestedNameSpecifierLoc QualifierLoc
,
1135 SourceLocation TemplateKWLoc
,
1136 const IdentifierInfo
*Name
,
1137 SourceLocation NameLoc
,
1138 TemplateArgumentListInfo
&Args
,
1139 bool AllowInjectedClassName
) {
1140 // Rebuild the template name.
1141 // TODO: avoid TemplateName abstraction
1143 SS
.Adopt(QualifierLoc
);
1144 TemplateName InstName
= getDerived().RebuildTemplateName(
1145 SS
, TemplateKWLoc
, *Name
, NameLoc
, QualType(), nullptr,
1146 AllowInjectedClassName
);
1148 if (InstName
.isNull())
1151 // If it's still dependent, make a dependent specialization.
1152 if (InstName
.getAsDependentTemplateName())
1153 return SemaRef
.Context
.getDependentTemplateSpecializationType(
1154 Keyword
, QualifierLoc
.getNestedNameSpecifier(), Name
,
1157 // Otherwise, make an elaborated type wrapping a non-dependent
1160 getDerived().RebuildTemplateSpecializationType(InstName
, NameLoc
, Args
);
1163 return SemaRef
.Context
.getElaboratedType(
1164 Keyword
, QualifierLoc
.getNestedNameSpecifier(), T
);
1167 /// Build a new typename type that refers to an identifier.
1169 /// By default, performs semantic analysis when building the typename type
1170 /// (or elaborated type). Subclasses may override this routine to provide
1171 /// different behavior.
1172 QualType
RebuildDependentNameType(ElaboratedTypeKeyword Keyword
,
1173 SourceLocation KeywordLoc
,
1174 NestedNameSpecifierLoc QualifierLoc
,
1175 const IdentifierInfo
*Id
,
1176 SourceLocation IdLoc
,
1177 bool DeducedTSTContext
) {
1179 SS
.Adopt(QualifierLoc
);
1181 if (QualifierLoc
.getNestedNameSpecifier()->isDependent()) {
1182 // If the name is still dependent, just build a new dependent name type.
1183 if (!SemaRef
.computeDeclContext(SS
))
1184 return SemaRef
.Context
.getDependentNameType(Keyword
,
1185 QualifierLoc
.getNestedNameSpecifier(),
1189 if (Keyword
== ElaboratedTypeKeyword::None
||
1190 Keyword
== ElaboratedTypeKeyword::Typename
) {
1191 return SemaRef
.CheckTypenameType(Keyword
, KeywordLoc
, QualifierLoc
,
1192 *Id
, IdLoc
, DeducedTSTContext
);
1195 TagTypeKind Kind
= TypeWithKeyword::getTagTypeKindForKeyword(Keyword
);
1197 // We had a dependent elaborated-type-specifier that has been transformed
1198 // into a non-dependent elaborated-type-specifier. Find the tag we're
1200 LookupResult
Result(SemaRef
, Id
, IdLoc
, Sema::LookupTagName
);
1201 DeclContext
*DC
= SemaRef
.computeDeclContext(SS
, false);
1205 if (SemaRef
.RequireCompleteDeclContext(SS
, DC
))
1208 TagDecl
*Tag
= nullptr;
1209 SemaRef
.LookupQualifiedName(Result
, DC
);
1210 switch (Result
.getResultKind()) {
1211 case LookupResult::NotFound
:
1212 case LookupResult::NotFoundInCurrentInstantiation
:
1215 case LookupResult::Found
:
1216 Tag
= Result
.getAsSingle
<TagDecl
>();
1219 case LookupResult::FoundOverloaded
:
1220 case LookupResult::FoundUnresolvedValue
:
1221 llvm_unreachable("Tag lookup cannot find non-tags");
1223 case LookupResult::Ambiguous
:
1224 // Let the LookupResult structure handle ambiguities.
1229 // Check where the name exists but isn't a tag type and use that to emit
1230 // better diagnostics.
1231 LookupResult
Result(SemaRef
, Id
, IdLoc
, Sema::LookupTagName
);
1232 SemaRef
.LookupQualifiedName(Result
, DC
);
1233 switch (Result
.getResultKind()) {
1234 case LookupResult::Found
:
1235 case LookupResult::FoundOverloaded
:
1236 case LookupResult::FoundUnresolvedValue
: {
1237 NamedDecl
*SomeDecl
= Result
.getRepresentativeDecl();
1238 Sema::NonTagKind NTK
= SemaRef
.getNonTagTypeDeclKind(SomeDecl
, Kind
);
1239 SemaRef
.Diag(IdLoc
, diag::err_tag_reference_non_tag
)
1240 << SomeDecl
<< NTK
<< llvm::to_underlying(Kind
);
1241 SemaRef
.Diag(SomeDecl
->getLocation(), diag::note_declared_at
);
1245 SemaRef
.Diag(IdLoc
, diag::err_not_tag_in_scope
)
1246 << llvm::to_underlying(Kind
) << Id
<< DC
1247 << QualifierLoc
.getSourceRange();
1253 if (!SemaRef
.isAcceptableTagRedeclaration(Tag
, Kind
, /*isDefinition*/false,
1255 SemaRef
.Diag(KeywordLoc
, diag::err_use_with_wrong_tag
) << Id
;
1256 SemaRef
.Diag(Tag
->getLocation(), diag::note_previous_use
);
1260 // Build the elaborated-type-specifier type.
1261 QualType T
= SemaRef
.Context
.getTypeDeclType(Tag
);
1262 return SemaRef
.Context
.getElaboratedType(Keyword
,
1263 QualifierLoc
.getNestedNameSpecifier(),
1267 /// Build a new pack expansion type.
1269 /// By default, builds a new PackExpansionType type from the given pattern.
1270 /// Subclasses may override this routine to provide different behavior.
1271 QualType
RebuildPackExpansionType(QualType Pattern
, SourceRange PatternRange
,
1272 SourceLocation EllipsisLoc
,
1273 std::optional
<unsigned> NumExpansions
) {
1274 return getSema().CheckPackExpansion(Pattern
, PatternRange
, EllipsisLoc
,
1278 /// Build a new atomic type given its value type.
1280 /// By default, performs semantic analysis when building the atomic type.
1281 /// Subclasses may override this routine to provide different behavior.
1282 QualType
RebuildAtomicType(QualType ValueType
, SourceLocation KWLoc
);
1284 /// Build a new pipe type given its value type.
1285 QualType
RebuildPipeType(QualType ValueType
, SourceLocation KWLoc
,
1288 /// Build a bit-precise int given its value type.
1289 QualType
RebuildBitIntType(bool IsUnsigned
, unsigned NumBits
,
1290 SourceLocation Loc
);
1292 /// Build a dependent bit-precise int given its value type.
1293 QualType
RebuildDependentBitIntType(bool IsUnsigned
, Expr
*NumBitsExpr
,
1294 SourceLocation Loc
);
1296 /// Build a new template name given a nested name specifier, a flag
1297 /// indicating whether the "template" keyword was provided, and the template
1298 /// that the template name refers to.
1300 /// By default, builds the new template name directly. Subclasses may override
1301 /// this routine to provide different behavior.
1302 TemplateName
RebuildTemplateName(CXXScopeSpec
&SS
,
1304 TemplateDecl
*Template
);
1306 /// Build a new template name given a nested name specifier and the
1307 /// name that is referred to as a template.
1309 /// By default, performs semantic analysis to determine whether the name can
1310 /// be resolved to a specific template, then builds the appropriate kind of
1311 /// template name. Subclasses may override this routine to provide different
1313 TemplateName
RebuildTemplateName(CXXScopeSpec
&SS
,
1314 SourceLocation TemplateKWLoc
,
1315 const IdentifierInfo
&Name
,
1316 SourceLocation NameLoc
, QualType ObjectType
,
1317 NamedDecl
*FirstQualifierInScope
,
1318 bool AllowInjectedClassName
);
1320 /// Build a new template name given a nested name specifier and the
1321 /// overloaded operator name that is referred to as a template.
1323 /// By default, performs semantic analysis to determine whether the name can
1324 /// be resolved to a specific template, then builds the appropriate kind of
1325 /// template name. Subclasses may override this routine to provide different
1327 TemplateName
RebuildTemplateName(CXXScopeSpec
&SS
,
1328 SourceLocation TemplateKWLoc
,
1329 OverloadedOperatorKind Operator
,
1330 SourceLocation NameLoc
, QualType ObjectType
,
1331 bool AllowInjectedClassName
);
1333 /// Build a new template name given a template template parameter pack
1336 /// By default, performs semantic analysis to determine whether the name can
1337 /// be resolved to a specific template, then builds the appropriate kind of
1338 /// template name. Subclasses may override this routine to provide different
1340 TemplateName
RebuildTemplateName(const TemplateArgument
&ArgPack
,
1341 Decl
*AssociatedDecl
, unsigned Index
,
1343 return getSema().Context
.getSubstTemplateTemplateParmPack(
1344 ArgPack
, AssociatedDecl
, Index
, Final
);
1347 /// Build a new compound statement.
1349 /// By default, performs semantic analysis to build the new statement.
1350 /// Subclasses may override this routine to provide different behavior.
1351 StmtResult
RebuildCompoundStmt(SourceLocation LBraceLoc
,
1352 MultiStmtArg Statements
,
1353 SourceLocation RBraceLoc
,
1355 return getSema().ActOnCompoundStmt(LBraceLoc
, RBraceLoc
, Statements
,
1359 /// Build a new case statement.
1361 /// By default, performs semantic analysis to build the new statement.
1362 /// Subclasses may override this routine to provide different behavior.
1363 StmtResult
RebuildCaseStmt(SourceLocation CaseLoc
,
1365 SourceLocation EllipsisLoc
,
1367 SourceLocation ColonLoc
) {
1368 return getSema().ActOnCaseStmt(CaseLoc
, LHS
, EllipsisLoc
, RHS
,
1372 /// Attach the body to a new case statement.
1374 /// By default, performs semantic analysis to build the new statement.
1375 /// Subclasses may override this routine to provide different behavior.
1376 StmtResult
RebuildCaseStmtBody(Stmt
*S
, Stmt
*Body
) {
1377 getSema().ActOnCaseStmtBody(S
, Body
);
1381 /// Build a new default statement.
1383 /// By default, performs semantic analysis to build the new statement.
1384 /// Subclasses may override this routine to provide different behavior.
1385 StmtResult
RebuildDefaultStmt(SourceLocation DefaultLoc
,
1386 SourceLocation ColonLoc
,
1388 return getSema().ActOnDefaultStmt(DefaultLoc
, ColonLoc
, SubStmt
,
1389 /*CurScope=*/nullptr);
1392 /// Build a new label statement.
1394 /// By default, performs semantic analysis to build the new statement.
1395 /// Subclasses may override this routine to provide different behavior.
1396 StmtResult
RebuildLabelStmt(SourceLocation IdentLoc
, LabelDecl
*L
,
1397 SourceLocation ColonLoc
, Stmt
*SubStmt
) {
1398 return SemaRef
.ActOnLabelStmt(IdentLoc
, L
, ColonLoc
, SubStmt
);
1401 /// Build a new attributed statement.
1403 /// By default, performs semantic analysis to build the new statement.
1404 /// Subclasses may override this routine to provide different behavior.
1405 StmtResult
RebuildAttributedStmt(SourceLocation AttrLoc
,
1406 ArrayRef
<const Attr
*> Attrs
,
1408 if (SemaRef
.CheckRebuiltStmtAttributes(Attrs
))
1410 return SemaRef
.BuildAttributedStmt(AttrLoc
, Attrs
, SubStmt
);
1413 /// Build a new "if" statement.
1415 /// By default, performs semantic analysis to build the new statement.
1416 /// Subclasses may override this routine to provide different behavior.
1417 StmtResult
RebuildIfStmt(SourceLocation IfLoc
, IfStatementKind Kind
,
1418 SourceLocation LParenLoc
, Sema::ConditionResult Cond
,
1419 SourceLocation RParenLoc
, Stmt
*Init
, Stmt
*Then
,
1420 SourceLocation ElseLoc
, Stmt
*Else
) {
1421 return getSema().ActOnIfStmt(IfLoc
, Kind
, LParenLoc
, Init
, Cond
, RParenLoc
,
1422 Then
, ElseLoc
, Else
);
1425 /// Start building a new switch statement.
1427 /// By default, performs semantic analysis to build the new statement.
1428 /// Subclasses may override this routine to provide different behavior.
1429 StmtResult
RebuildSwitchStmtStart(SourceLocation SwitchLoc
,
1430 SourceLocation LParenLoc
, Stmt
*Init
,
1431 Sema::ConditionResult Cond
,
1432 SourceLocation RParenLoc
) {
1433 return getSema().ActOnStartOfSwitchStmt(SwitchLoc
, LParenLoc
, Init
, Cond
,
1437 /// Attach the body to the switch statement.
1439 /// By default, performs semantic analysis to build the new statement.
1440 /// Subclasses may override this routine to provide different behavior.
1441 StmtResult
RebuildSwitchStmtBody(SourceLocation SwitchLoc
,
1442 Stmt
*Switch
, Stmt
*Body
) {
1443 return getSema().ActOnFinishSwitchStmt(SwitchLoc
, Switch
, Body
);
1446 /// Build a new while statement.
1448 /// By default, performs semantic analysis to build the new statement.
1449 /// Subclasses may override this routine to provide different behavior.
1450 StmtResult
RebuildWhileStmt(SourceLocation WhileLoc
, SourceLocation LParenLoc
,
1451 Sema::ConditionResult Cond
,
1452 SourceLocation RParenLoc
, Stmt
*Body
) {
1453 return getSema().ActOnWhileStmt(WhileLoc
, LParenLoc
, Cond
, RParenLoc
, Body
);
1456 /// Build a new do-while statement.
1458 /// By default, performs semantic analysis to build the new statement.
1459 /// Subclasses may override this routine to provide different behavior.
1460 StmtResult
RebuildDoStmt(SourceLocation DoLoc
, Stmt
*Body
,
1461 SourceLocation WhileLoc
, SourceLocation LParenLoc
,
1462 Expr
*Cond
, SourceLocation RParenLoc
) {
1463 return getSema().ActOnDoStmt(DoLoc
, Body
, WhileLoc
, LParenLoc
,
1467 /// Build a new for statement.
1469 /// By default, performs semantic analysis to build the new statement.
1470 /// Subclasses may override this routine to provide different behavior.
1471 StmtResult
RebuildForStmt(SourceLocation ForLoc
, SourceLocation LParenLoc
,
1472 Stmt
*Init
, Sema::ConditionResult Cond
,
1473 Sema::FullExprArg Inc
, SourceLocation RParenLoc
,
1475 return getSema().ActOnForStmt(ForLoc
, LParenLoc
, Init
, Cond
,
1476 Inc
, RParenLoc
, Body
);
1479 /// Build a new goto statement.
1481 /// By default, performs semantic analysis to build the new statement.
1482 /// Subclasses may override this routine to provide different behavior.
1483 StmtResult
RebuildGotoStmt(SourceLocation GotoLoc
, SourceLocation LabelLoc
,
1485 return getSema().ActOnGotoStmt(GotoLoc
, LabelLoc
, Label
);
1488 /// Build a new indirect goto statement.
1490 /// By default, performs semantic analysis to build the new statement.
1491 /// Subclasses may override this routine to provide different behavior.
1492 StmtResult
RebuildIndirectGotoStmt(SourceLocation GotoLoc
,
1493 SourceLocation StarLoc
,
1495 return getSema().ActOnIndirectGotoStmt(GotoLoc
, StarLoc
, Target
);
1498 /// Build a new return statement.
1500 /// By default, performs semantic analysis to build the new statement.
1501 /// Subclasses may override this routine to provide different behavior.
1502 StmtResult
RebuildReturnStmt(SourceLocation ReturnLoc
, Expr
*Result
) {
1503 return getSema().BuildReturnStmt(ReturnLoc
, Result
);
1506 /// Build a new declaration statement.
1508 /// By default, performs semantic analysis to build the new statement.
1509 /// Subclasses may override this routine to provide different behavior.
1510 StmtResult
RebuildDeclStmt(MutableArrayRef
<Decl
*> Decls
,
1511 SourceLocation StartLoc
, SourceLocation EndLoc
) {
1512 Sema::DeclGroupPtrTy DG
= getSema().BuildDeclaratorGroup(Decls
);
1513 return getSema().ActOnDeclStmt(DG
, StartLoc
, EndLoc
);
1516 /// Build a new inline asm statement.
1518 /// By default, performs semantic analysis to build the new statement.
1519 /// Subclasses may override this routine to provide different behavior.
1520 StmtResult
RebuildGCCAsmStmt(SourceLocation AsmLoc
, bool IsSimple
,
1521 bool IsVolatile
, unsigned NumOutputs
,
1522 unsigned NumInputs
, IdentifierInfo
**Names
,
1523 MultiExprArg Constraints
, MultiExprArg Exprs
,
1524 Expr
*AsmString
, MultiExprArg Clobbers
,
1526 SourceLocation RParenLoc
) {
1527 return getSema().ActOnGCCAsmStmt(AsmLoc
, IsSimple
, IsVolatile
, NumOutputs
,
1528 NumInputs
, Names
, Constraints
, Exprs
,
1529 AsmString
, Clobbers
, NumLabels
, RParenLoc
);
1532 /// Build a new MS style inline asm statement.
1534 /// By default, performs semantic analysis to build the new statement.
1535 /// Subclasses may override this routine to provide different behavior.
1536 StmtResult
RebuildMSAsmStmt(SourceLocation AsmLoc
, SourceLocation LBraceLoc
,
1537 ArrayRef
<Token
> AsmToks
,
1538 StringRef AsmString
,
1539 unsigned NumOutputs
, unsigned NumInputs
,
1540 ArrayRef
<StringRef
> Constraints
,
1541 ArrayRef
<StringRef
> Clobbers
,
1542 ArrayRef
<Expr
*> Exprs
,
1543 SourceLocation EndLoc
) {
1544 return getSema().ActOnMSAsmStmt(AsmLoc
, LBraceLoc
, AsmToks
, AsmString
,
1545 NumOutputs
, NumInputs
,
1546 Constraints
, Clobbers
, Exprs
, EndLoc
);
1549 /// Build a new co_return statement.
1551 /// By default, performs semantic analysis to build the new statement.
1552 /// Subclasses may override this routine to provide different behavior.
1553 StmtResult
RebuildCoreturnStmt(SourceLocation CoreturnLoc
, Expr
*Result
,
1555 return getSema().BuildCoreturnStmt(CoreturnLoc
, Result
, IsImplicit
);
1558 /// Build a new co_await expression.
1560 /// By default, performs semantic analysis to build the new expression.
1561 /// Subclasses may override this routine to provide different behavior.
1562 ExprResult
RebuildCoawaitExpr(SourceLocation CoawaitLoc
, Expr
*Operand
,
1563 UnresolvedLookupExpr
*OpCoawaitLookup
,
1565 // This function rebuilds a coawait-expr given its operator.
1566 // For an explicit coawait-expr, the rebuild involves the full set
1567 // of transformations performed by BuildUnresolvedCoawaitExpr(),
1568 // including calling await_transform().
1569 // For an implicit coawait-expr, we need to rebuild the "operator
1570 // coawait" but not await_transform(), so use BuildResolvedCoawaitExpr().
1571 // This mirrors how the implicit CoawaitExpr is originally created
1572 // in Sema::ActOnCoroutineBodyStart().
1574 ExprResult Suspend
= getSema().BuildOperatorCoawaitCall(
1575 CoawaitLoc
, Operand
, OpCoawaitLookup
);
1576 if (Suspend
.isInvalid())
1578 return getSema().BuildResolvedCoawaitExpr(CoawaitLoc
, Operand
,
1579 Suspend
.get(), true);
1582 return getSema().BuildUnresolvedCoawaitExpr(CoawaitLoc
, Operand
,
1586 /// Build a new co_await expression.
1588 /// By default, performs semantic analysis to build the new expression.
1589 /// Subclasses may override this routine to provide different behavior.
1590 ExprResult
RebuildDependentCoawaitExpr(SourceLocation CoawaitLoc
,
1592 UnresolvedLookupExpr
*Lookup
) {
1593 return getSema().BuildUnresolvedCoawaitExpr(CoawaitLoc
, Result
, Lookup
);
1596 /// Build a new co_yield expression.
1598 /// By default, performs semantic analysis to build the new expression.
1599 /// Subclasses may override this routine to provide different behavior.
1600 ExprResult
RebuildCoyieldExpr(SourceLocation CoyieldLoc
, Expr
*Result
) {
1601 return getSema().BuildCoyieldExpr(CoyieldLoc
, Result
);
1604 StmtResult
RebuildCoroutineBodyStmt(CoroutineBodyStmt::CtorArgs Args
) {
1605 return getSema().BuildCoroutineBodyStmt(Args
);
1608 /// Build a new Objective-C \@try statement.
1610 /// By default, performs semantic analysis to build the new statement.
1611 /// Subclasses may override this routine to provide different behavior.
1612 StmtResult
RebuildObjCAtTryStmt(SourceLocation AtLoc
,
1614 MultiStmtArg CatchStmts
,
1616 return getSema().ObjC().ActOnObjCAtTryStmt(AtLoc
, TryBody
, CatchStmts
,
1620 /// Rebuild an Objective-C exception declaration.
1622 /// By default, performs semantic analysis to build the new declaration.
1623 /// Subclasses may override this routine to provide different behavior.
1624 VarDecl
*RebuildObjCExceptionDecl(VarDecl
*ExceptionDecl
,
1625 TypeSourceInfo
*TInfo
, QualType T
) {
1626 return getSema().ObjC().BuildObjCExceptionDecl(
1627 TInfo
, T
, ExceptionDecl
->getInnerLocStart(),
1628 ExceptionDecl
->getLocation(), ExceptionDecl
->getIdentifier());
1631 /// Build a new Objective-C \@catch statement.
1633 /// By default, performs semantic analysis to build the new statement.
1634 /// Subclasses may override this routine to provide different behavior.
1635 StmtResult
RebuildObjCAtCatchStmt(SourceLocation AtLoc
,
1636 SourceLocation RParenLoc
,
1639 return getSema().ObjC().ActOnObjCAtCatchStmt(AtLoc
, RParenLoc
, Var
, Body
);
1642 /// Build a new Objective-C \@finally statement.
1644 /// By default, performs semantic analysis to build the new statement.
1645 /// Subclasses may override this routine to provide different behavior.
1646 StmtResult
RebuildObjCAtFinallyStmt(SourceLocation AtLoc
,
1648 return getSema().ObjC().ActOnObjCAtFinallyStmt(AtLoc
, Body
);
1651 /// Build a new Objective-C \@throw statement.
1653 /// By default, performs semantic analysis to build the new statement.
1654 /// Subclasses may override this routine to provide different behavior.
1655 StmtResult
RebuildObjCAtThrowStmt(SourceLocation AtLoc
,
1657 return getSema().ObjC().BuildObjCAtThrowStmt(AtLoc
, Operand
);
1660 /// Build a new OpenMP Canonical loop.
1662 /// Ensures that the outermost loop in @p LoopStmt is wrapped by a
1663 /// OMPCanonicalLoop.
1664 StmtResult
RebuildOMPCanonicalLoop(Stmt
*LoopStmt
) {
1665 return getSema().OpenMP().ActOnOpenMPCanonicalLoop(LoopStmt
);
1668 /// Build a new OpenMP executable directive.
1670 /// By default, performs semantic analysis to build the new statement.
1671 /// Subclasses may override this routine to provide different behavior.
1672 StmtResult
RebuildOMPExecutableDirective(OpenMPDirectiveKind Kind
,
1673 DeclarationNameInfo DirName
,
1674 OpenMPDirectiveKind CancelRegion
,
1675 ArrayRef
<OMPClause
*> Clauses
,
1676 Stmt
*AStmt
, SourceLocation StartLoc
,
1677 SourceLocation EndLoc
) {
1679 return getSema().OpenMP().ActOnOpenMPExecutableDirective(
1680 Kind
, DirName
, CancelRegion
, Clauses
, AStmt
, StartLoc
, EndLoc
);
1683 /// Build a new OpenMP informational directive.
1684 StmtResult
RebuildOMPInformationalDirective(OpenMPDirectiveKind Kind
,
1685 DeclarationNameInfo DirName
,
1686 ArrayRef
<OMPClause
*> Clauses
,
1688 SourceLocation StartLoc
,
1689 SourceLocation EndLoc
) {
1691 return getSema().OpenMP().ActOnOpenMPInformationalDirective(
1692 Kind
, DirName
, Clauses
, AStmt
, StartLoc
, EndLoc
);
1695 /// Build a new OpenMP 'if' clause.
1697 /// By default, performs semantic analysis to build the new OpenMP clause.
1698 /// Subclasses may override this routine to provide different behavior.
1699 OMPClause
*RebuildOMPIfClause(OpenMPDirectiveKind NameModifier
,
1700 Expr
*Condition
, SourceLocation StartLoc
,
1701 SourceLocation LParenLoc
,
1702 SourceLocation NameModifierLoc
,
1703 SourceLocation ColonLoc
,
1704 SourceLocation EndLoc
) {
1705 return getSema().OpenMP().ActOnOpenMPIfClause(
1706 NameModifier
, Condition
, StartLoc
, LParenLoc
, NameModifierLoc
, ColonLoc
,
1710 /// Build a new OpenMP 'final' clause.
1712 /// By default, performs semantic analysis to build the new OpenMP clause.
1713 /// Subclasses may override this routine to provide different behavior.
1714 OMPClause
*RebuildOMPFinalClause(Expr
*Condition
, SourceLocation StartLoc
,
1715 SourceLocation LParenLoc
,
1716 SourceLocation EndLoc
) {
1717 return getSema().OpenMP().ActOnOpenMPFinalClause(Condition
, StartLoc
,
1721 /// Build a new OpenMP 'num_threads' clause.
1723 /// By default, performs semantic analysis to build the new OpenMP clause.
1724 /// Subclasses may override this routine to provide different behavior.
1725 OMPClause
*RebuildOMPNumThreadsClause(Expr
*NumThreads
,
1726 SourceLocation StartLoc
,
1727 SourceLocation LParenLoc
,
1728 SourceLocation EndLoc
) {
1729 return getSema().OpenMP().ActOnOpenMPNumThreadsClause(NumThreads
, StartLoc
,
1733 /// Build a new OpenMP 'safelen' clause.
1735 /// By default, performs semantic analysis to build the new OpenMP clause.
1736 /// Subclasses may override this routine to provide different behavior.
1737 OMPClause
*RebuildOMPSafelenClause(Expr
*Len
, SourceLocation StartLoc
,
1738 SourceLocation LParenLoc
,
1739 SourceLocation EndLoc
) {
1740 return getSema().OpenMP().ActOnOpenMPSafelenClause(Len
, StartLoc
, LParenLoc
,
1744 /// Build a new OpenMP 'simdlen' clause.
1746 /// By default, performs semantic analysis to build the new OpenMP clause.
1747 /// Subclasses may override this routine to provide different behavior.
1748 OMPClause
*RebuildOMPSimdlenClause(Expr
*Len
, SourceLocation StartLoc
,
1749 SourceLocation LParenLoc
,
1750 SourceLocation EndLoc
) {
1751 return getSema().OpenMP().ActOnOpenMPSimdlenClause(Len
, StartLoc
, LParenLoc
,
1755 OMPClause
*RebuildOMPSizesClause(ArrayRef
<Expr
*> Sizes
,
1756 SourceLocation StartLoc
,
1757 SourceLocation LParenLoc
,
1758 SourceLocation EndLoc
) {
1759 return getSema().OpenMP().ActOnOpenMPSizesClause(Sizes
, StartLoc
, LParenLoc
,
1763 /// Build a new OpenMP 'permutation' clause.
1764 OMPClause
*RebuildOMPPermutationClause(ArrayRef
<Expr
*> PermExprs
,
1765 SourceLocation StartLoc
,
1766 SourceLocation LParenLoc
,
1767 SourceLocation EndLoc
) {
1768 return getSema().OpenMP().ActOnOpenMPPermutationClause(PermExprs
, StartLoc
,
1772 /// Build a new OpenMP 'full' clause.
1773 OMPClause
*RebuildOMPFullClause(SourceLocation StartLoc
,
1774 SourceLocation EndLoc
) {
1775 return getSema().OpenMP().ActOnOpenMPFullClause(StartLoc
, EndLoc
);
1778 /// Build a new OpenMP 'partial' clause.
1779 OMPClause
*RebuildOMPPartialClause(Expr
*Factor
, SourceLocation StartLoc
,
1780 SourceLocation LParenLoc
,
1781 SourceLocation EndLoc
) {
1782 return getSema().OpenMP().ActOnOpenMPPartialClause(Factor
, StartLoc
,
1786 /// Build a new OpenMP 'allocator' clause.
1788 /// By default, performs semantic analysis to build the new OpenMP clause.
1789 /// Subclasses may override this routine to provide different behavior.
1790 OMPClause
*RebuildOMPAllocatorClause(Expr
*A
, SourceLocation StartLoc
,
1791 SourceLocation LParenLoc
,
1792 SourceLocation EndLoc
) {
1793 return getSema().OpenMP().ActOnOpenMPAllocatorClause(A
, StartLoc
, LParenLoc
,
1797 /// Build a new OpenMP 'collapse' clause.
1799 /// By default, performs semantic analysis to build the new OpenMP clause.
1800 /// Subclasses may override this routine to provide different behavior.
1801 OMPClause
*RebuildOMPCollapseClause(Expr
*Num
, SourceLocation StartLoc
,
1802 SourceLocation LParenLoc
,
1803 SourceLocation EndLoc
) {
1804 return getSema().OpenMP().ActOnOpenMPCollapseClause(Num
, StartLoc
,
1808 /// Build a new OpenMP 'default' clause.
1810 /// By default, performs semantic analysis to build the new OpenMP clause.
1811 /// Subclasses may override this routine to provide different behavior.
1812 OMPClause
*RebuildOMPDefaultClause(DefaultKind Kind
, SourceLocation KindKwLoc
,
1813 SourceLocation StartLoc
,
1814 SourceLocation LParenLoc
,
1815 SourceLocation EndLoc
) {
1816 return getSema().OpenMP().ActOnOpenMPDefaultClause(
1817 Kind
, KindKwLoc
, StartLoc
, LParenLoc
, EndLoc
);
1820 /// Build a new OpenMP 'proc_bind' clause.
1822 /// By default, performs semantic analysis to build the new OpenMP clause.
1823 /// Subclasses may override this routine to provide different behavior.
1824 OMPClause
*RebuildOMPProcBindClause(ProcBindKind Kind
,
1825 SourceLocation KindKwLoc
,
1826 SourceLocation StartLoc
,
1827 SourceLocation LParenLoc
,
1828 SourceLocation EndLoc
) {
1829 return getSema().OpenMP().ActOnOpenMPProcBindClause(
1830 Kind
, KindKwLoc
, StartLoc
, LParenLoc
, EndLoc
);
1833 /// Build a new OpenMP 'schedule' clause.
1835 /// By default, performs semantic analysis to build the new OpenMP clause.
1836 /// Subclasses may override this routine to provide different behavior.
1837 OMPClause
*RebuildOMPScheduleClause(
1838 OpenMPScheduleClauseModifier M1
, OpenMPScheduleClauseModifier M2
,
1839 OpenMPScheduleClauseKind Kind
, Expr
*ChunkSize
, SourceLocation StartLoc
,
1840 SourceLocation LParenLoc
, SourceLocation M1Loc
, SourceLocation M2Loc
,
1841 SourceLocation KindLoc
, SourceLocation CommaLoc
, SourceLocation EndLoc
) {
1842 return getSema().OpenMP().ActOnOpenMPScheduleClause(
1843 M1
, M2
, Kind
, ChunkSize
, StartLoc
, LParenLoc
, M1Loc
, M2Loc
, KindLoc
,
1847 /// Build a new OpenMP 'ordered' clause.
1849 /// By default, performs semantic analysis to build the new OpenMP clause.
1850 /// Subclasses may override this routine to provide different behavior.
1851 OMPClause
*RebuildOMPOrderedClause(SourceLocation StartLoc
,
1852 SourceLocation EndLoc
,
1853 SourceLocation LParenLoc
, Expr
*Num
) {
1854 return getSema().OpenMP().ActOnOpenMPOrderedClause(StartLoc
, EndLoc
,
1858 /// Build a new OpenMP 'private' clause.
1860 /// By default, performs semantic analysis to build the new OpenMP clause.
1861 /// Subclasses may override this routine to provide different behavior.
1862 OMPClause
*RebuildOMPPrivateClause(ArrayRef
<Expr
*> VarList
,
1863 SourceLocation StartLoc
,
1864 SourceLocation LParenLoc
,
1865 SourceLocation EndLoc
) {
1866 return getSema().OpenMP().ActOnOpenMPPrivateClause(VarList
, StartLoc
,
1870 /// Build a new OpenMP 'firstprivate' clause.
1872 /// By default, performs semantic analysis to build the new OpenMP clause.
1873 /// Subclasses may override this routine to provide different behavior.
1874 OMPClause
*RebuildOMPFirstprivateClause(ArrayRef
<Expr
*> VarList
,
1875 SourceLocation StartLoc
,
1876 SourceLocation LParenLoc
,
1877 SourceLocation EndLoc
) {
1878 return getSema().OpenMP().ActOnOpenMPFirstprivateClause(VarList
, StartLoc
,
1882 /// Build a new OpenMP 'lastprivate' clause.
1884 /// By default, performs semantic analysis to build the new OpenMP clause.
1885 /// Subclasses may override this routine to provide different behavior.
1886 OMPClause
*RebuildOMPLastprivateClause(ArrayRef
<Expr
*> VarList
,
1887 OpenMPLastprivateModifier LPKind
,
1888 SourceLocation LPKindLoc
,
1889 SourceLocation ColonLoc
,
1890 SourceLocation StartLoc
,
1891 SourceLocation LParenLoc
,
1892 SourceLocation EndLoc
) {
1893 return getSema().OpenMP().ActOnOpenMPLastprivateClause(
1894 VarList
, LPKind
, LPKindLoc
, ColonLoc
, StartLoc
, LParenLoc
, EndLoc
);
1897 /// Build a new OpenMP 'shared' clause.
1899 /// By default, performs semantic analysis to build the new OpenMP clause.
1900 /// Subclasses may override this routine to provide different behavior.
1901 OMPClause
*RebuildOMPSharedClause(ArrayRef
<Expr
*> VarList
,
1902 SourceLocation StartLoc
,
1903 SourceLocation LParenLoc
,
1904 SourceLocation EndLoc
) {
1905 return getSema().OpenMP().ActOnOpenMPSharedClause(VarList
, StartLoc
,
1909 /// Build a new OpenMP 'reduction' clause.
1911 /// By default, performs semantic analysis to build the new statement.
1912 /// Subclasses may override this routine to provide different behavior.
1913 OMPClause
*RebuildOMPReductionClause(
1914 ArrayRef
<Expr
*> VarList
, OpenMPReductionClauseModifier Modifier
,
1915 SourceLocation StartLoc
, SourceLocation LParenLoc
,
1916 SourceLocation ModifierLoc
, SourceLocation ColonLoc
,
1917 SourceLocation EndLoc
, CXXScopeSpec
&ReductionIdScopeSpec
,
1918 const DeclarationNameInfo
&ReductionId
,
1919 ArrayRef
<Expr
*> UnresolvedReductions
) {
1920 return getSema().OpenMP().ActOnOpenMPReductionClause(
1921 VarList
, Modifier
, StartLoc
, LParenLoc
, ModifierLoc
, ColonLoc
, EndLoc
,
1922 ReductionIdScopeSpec
, ReductionId
, UnresolvedReductions
);
1925 /// Build a new OpenMP 'task_reduction' clause.
1927 /// By default, performs semantic analysis to build the new statement.
1928 /// Subclasses may override this routine to provide different behavior.
1929 OMPClause
*RebuildOMPTaskReductionClause(
1930 ArrayRef
<Expr
*> VarList
, SourceLocation StartLoc
,
1931 SourceLocation LParenLoc
, SourceLocation ColonLoc
, SourceLocation EndLoc
,
1932 CXXScopeSpec
&ReductionIdScopeSpec
,
1933 const DeclarationNameInfo
&ReductionId
,
1934 ArrayRef
<Expr
*> UnresolvedReductions
) {
1935 return getSema().OpenMP().ActOnOpenMPTaskReductionClause(
1936 VarList
, StartLoc
, LParenLoc
, ColonLoc
, EndLoc
, ReductionIdScopeSpec
,
1937 ReductionId
, UnresolvedReductions
);
1940 /// Build a new OpenMP 'in_reduction' clause.
1942 /// By default, performs semantic analysis to build the new statement.
1943 /// Subclasses may override this routine to provide different behavior.
1945 RebuildOMPInReductionClause(ArrayRef
<Expr
*> VarList
, SourceLocation StartLoc
,
1946 SourceLocation LParenLoc
, SourceLocation ColonLoc
,
1947 SourceLocation EndLoc
,
1948 CXXScopeSpec
&ReductionIdScopeSpec
,
1949 const DeclarationNameInfo
&ReductionId
,
1950 ArrayRef
<Expr
*> UnresolvedReductions
) {
1951 return getSema().OpenMP().ActOnOpenMPInReductionClause(
1952 VarList
, StartLoc
, LParenLoc
, ColonLoc
, EndLoc
, ReductionIdScopeSpec
,
1953 ReductionId
, UnresolvedReductions
);
1956 /// Build a new OpenMP 'linear' clause.
1958 /// By default, performs semantic analysis to build the new OpenMP clause.
1959 /// Subclasses may override this routine to provide different behavior.
1960 OMPClause
*RebuildOMPLinearClause(
1961 ArrayRef
<Expr
*> VarList
, Expr
*Step
, SourceLocation StartLoc
,
1962 SourceLocation LParenLoc
, OpenMPLinearClauseKind Modifier
,
1963 SourceLocation ModifierLoc
, SourceLocation ColonLoc
,
1964 SourceLocation StepModifierLoc
, SourceLocation EndLoc
) {
1965 return getSema().OpenMP().ActOnOpenMPLinearClause(
1966 VarList
, Step
, StartLoc
, LParenLoc
, Modifier
, ModifierLoc
, ColonLoc
,
1967 StepModifierLoc
, EndLoc
);
1970 /// Build a new OpenMP 'aligned' clause.
1972 /// By default, performs semantic analysis to build the new OpenMP clause.
1973 /// Subclasses may override this routine to provide different behavior.
1974 OMPClause
*RebuildOMPAlignedClause(ArrayRef
<Expr
*> VarList
, Expr
*Alignment
,
1975 SourceLocation StartLoc
,
1976 SourceLocation LParenLoc
,
1977 SourceLocation ColonLoc
,
1978 SourceLocation EndLoc
) {
1979 return getSema().OpenMP().ActOnOpenMPAlignedClause(
1980 VarList
, Alignment
, StartLoc
, LParenLoc
, ColonLoc
, EndLoc
);
1983 /// Build a new OpenMP 'copyin' clause.
1985 /// By default, performs semantic analysis to build the new OpenMP clause.
1986 /// Subclasses may override this routine to provide different behavior.
1987 OMPClause
*RebuildOMPCopyinClause(ArrayRef
<Expr
*> VarList
,
1988 SourceLocation StartLoc
,
1989 SourceLocation LParenLoc
,
1990 SourceLocation EndLoc
) {
1991 return getSema().OpenMP().ActOnOpenMPCopyinClause(VarList
, StartLoc
,
1995 /// Build a new OpenMP 'copyprivate' clause.
1997 /// By default, performs semantic analysis to build the new OpenMP clause.
1998 /// Subclasses may override this routine to provide different behavior.
1999 OMPClause
*RebuildOMPCopyprivateClause(ArrayRef
<Expr
*> VarList
,
2000 SourceLocation StartLoc
,
2001 SourceLocation LParenLoc
,
2002 SourceLocation EndLoc
) {
2003 return getSema().OpenMP().ActOnOpenMPCopyprivateClause(VarList
, StartLoc
,
2007 /// Build a new OpenMP 'flush' pseudo clause.
2009 /// By default, performs semantic analysis to build the new OpenMP clause.
2010 /// Subclasses may override this routine to provide different behavior.
2011 OMPClause
*RebuildOMPFlushClause(ArrayRef
<Expr
*> VarList
,
2012 SourceLocation StartLoc
,
2013 SourceLocation LParenLoc
,
2014 SourceLocation EndLoc
) {
2015 return getSema().OpenMP().ActOnOpenMPFlushClause(VarList
, StartLoc
,
2019 /// Build a new OpenMP 'depobj' pseudo clause.
2021 /// By default, performs semantic analysis to build the new OpenMP clause.
2022 /// Subclasses may override this routine to provide different behavior.
2023 OMPClause
*RebuildOMPDepobjClause(Expr
*Depobj
, SourceLocation StartLoc
,
2024 SourceLocation LParenLoc
,
2025 SourceLocation EndLoc
) {
2026 return getSema().OpenMP().ActOnOpenMPDepobjClause(Depobj
, StartLoc
,
2030 /// Build a new OpenMP 'depend' pseudo clause.
2032 /// By default, performs semantic analysis to build the new OpenMP clause.
2033 /// Subclasses may override this routine to provide different behavior.
2034 OMPClause
*RebuildOMPDependClause(OMPDependClause::DependDataTy Data
,
2035 Expr
*DepModifier
, ArrayRef
<Expr
*> VarList
,
2036 SourceLocation StartLoc
,
2037 SourceLocation LParenLoc
,
2038 SourceLocation EndLoc
) {
2039 return getSema().OpenMP().ActOnOpenMPDependClause(
2040 Data
, DepModifier
, VarList
, StartLoc
, LParenLoc
, EndLoc
);
2043 /// Build a new OpenMP 'device' clause.
2045 /// By default, performs semantic analysis to build the new statement.
2046 /// Subclasses may override this routine to provide different behavior.
2047 OMPClause
*RebuildOMPDeviceClause(OpenMPDeviceClauseModifier Modifier
,
2048 Expr
*Device
, SourceLocation StartLoc
,
2049 SourceLocation LParenLoc
,
2050 SourceLocation ModifierLoc
,
2051 SourceLocation EndLoc
) {
2052 return getSema().OpenMP().ActOnOpenMPDeviceClause(
2053 Modifier
, Device
, StartLoc
, LParenLoc
, ModifierLoc
, EndLoc
);
2056 /// Build a new OpenMP 'map' clause.
2058 /// By default, performs semantic analysis to build the new OpenMP clause.
2059 /// Subclasses may override this routine to provide different behavior.
2060 OMPClause
*RebuildOMPMapClause(
2061 Expr
*IteratorModifier
, ArrayRef
<OpenMPMapModifierKind
> MapTypeModifiers
,
2062 ArrayRef
<SourceLocation
> MapTypeModifiersLoc
,
2063 CXXScopeSpec MapperIdScopeSpec
, DeclarationNameInfo MapperId
,
2064 OpenMPMapClauseKind MapType
, bool IsMapTypeImplicit
,
2065 SourceLocation MapLoc
, SourceLocation ColonLoc
, ArrayRef
<Expr
*> VarList
,
2066 const OMPVarListLocTy
&Locs
, ArrayRef
<Expr
*> UnresolvedMappers
) {
2067 return getSema().OpenMP().ActOnOpenMPMapClause(
2068 IteratorModifier
, MapTypeModifiers
, MapTypeModifiersLoc
,
2069 MapperIdScopeSpec
, MapperId
, MapType
, IsMapTypeImplicit
, MapLoc
,
2070 ColonLoc
, VarList
, Locs
,
2071 /*NoDiagnose=*/false, UnresolvedMappers
);
2074 /// Build a new OpenMP 'allocate' clause.
2076 /// By default, performs semantic analysis to build the new OpenMP clause.
2077 /// Subclasses may override this routine to provide different behavior.
2078 OMPClause
*RebuildOMPAllocateClause(Expr
*Allocate
,
2079 OpenMPAllocateClauseModifier ACModifier
,
2080 ArrayRef
<Expr
*> VarList
,
2081 SourceLocation StartLoc
,
2082 SourceLocation LParenLoc
,
2083 SourceLocation ColonLoc
,
2084 SourceLocation EndLoc
) {
2085 return getSema().OpenMP().ActOnOpenMPAllocateClause(
2086 Allocate
, ACModifier
, VarList
, StartLoc
, LParenLoc
, ColonLoc
, EndLoc
);
2089 /// Build a new OpenMP 'num_teams' clause.
2091 /// By default, performs semantic analysis to build the new statement.
2092 /// Subclasses may override this routine to provide different behavior.
2093 OMPClause
*RebuildOMPNumTeamsClause(ArrayRef
<Expr
*> VarList
,
2094 SourceLocation StartLoc
,
2095 SourceLocation LParenLoc
,
2096 SourceLocation EndLoc
) {
2097 return getSema().OpenMP().ActOnOpenMPNumTeamsClause(VarList
, StartLoc
,
2101 /// Build a new OpenMP 'thread_limit' clause.
2103 /// By default, performs semantic analysis to build the new statement.
2104 /// Subclasses may override this routine to provide different behavior.
2105 OMPClause
*RebuildOMPThreadLimitClause(ArrayRef
<Expr
*> VarList
,
2106 SourceLocation StartLoc
,
2107 SourceLocation LParenLoc
,
2108 SourceLocation EndLoc
) {
2109 return getSema().OpenMP().ActOnOpenMPThreadLimitClause(VarList
, StartLoc
,
2113 /// Build a new OpenMP 'priority' clause.
2115 /// By default, performs semantic analysis to build the new statement.
2116 /// Subclasses may override this routine to provide different behavior.
2117 OMPClause
*RebuildOMPPriorityClause(Expr
*Priority
, SourceLocation StartLoc
,
2118 SourceLocation LParenLoc
,
2119 SourceLocation EndLoc
) {
2120 return getSema().OpenMP().ActOnOpenMPPriorityClause(Priority
, StartLoc
,
2124 /// Build a new OpenMP 'grainsize' clause.
2126 /// By default, performs semantic analysis to build the new statement.
2127 /// Subclasses may override this routine to provide different behavior.
2128 OMPClause
*RebuildOMPGrainsizeClause(OpenMPGrainsizeClauseModifier Modifier
,
2129 Expr
*Device
, SourceLocation StartLoc
,
2130 SourceLocation LParenLoc
,
2131 SourceLocation ModifierLoc
,
2132 SourceLocation EndLoc
) {
2133 return getSema().OpenMP().ActOnOpenMPGrainsizeClause(
2134 Modifier
, Device
, StartLoc
, LParenLoc
, ModifierLoc
, EndLoc
);
2137 /// Build a new OpenMP 'num_tasks' clause.
2139 /// By default, performs semantic analysis to build the new statement.
2140 /// Subclasses may override this routine to provide different behavior.
2141 OMPClause
*RebuildOMPNumTasksClause(OpenMPNumTasksClauseModifier Modifier
,
2142 Expr
*NumTasks
, SourceLocation StartLoc
,
2143 SourceLocation LParenLoc
,
2144 SourceLocation ModifierLoc
,
2145 SourceLocation EndLoc
) {
2146 return getSema().OpenMP().ActOnOpenMPNumTasksClause(
2147 Modifier
, NumTasks
, StartLoc
, LParenLoc
, ModifierLoc
, EndLoc
);
2150 /// Build a new OpenMP 'hint' clause.
2152 /// By default, performs semantic analysis to build the new statement.
2153 /// Subclasses may override this routine to provide different behavior.
2154 OMPClause
*RebuildOMPHintClause(Expr
*Hint
, SourceLocation StartLoc
,
2155 SourceLocation LParenLoc
,
2156 SourceLocation EndLoc
) {
2157 return getSema().OpenMP().ActOnOpenMPHintClause(Hint
, StartLoc
, LParenLoc
,
2161 /// Build a new OpenMP 'detach' clause.
2163 /// By default, performs semantic analysis to build the new statement.
2164 /// Subclasses may override this routine to provide different behavior.
2165 OMPClause
*RebuildOMPDetachClause(Expr
*Evt
, SourceLocation StartLoc
,
2166 SourceLocation LParenLoc
,
2167 SourceLocation EndLoc
) {
2168 return getSema().OpenMP().ActOnOpenMPDetachClause(Evt
, StartLoc
, LParenLoc
,
2172 /// Build a new OpenMP 'dist_schedule' clause.
2174 /// By default, performs semantic analysis to build the new OpenMP clause.
2175 /// Subclasses may override this routine to provide different behavior.
2177 RebuildOMPDistScheduleClause(OpenMPDistScheduleClauseKind Kind
,
2178 Expr
*ChunkSize
, SourceLocation StartLoc
,
2179 SourceLocation LParenLoc
, SourceLocation KindLoc
,
2180 SourceLocation CommaLoc
, SourceLocation EndLoc
) {
2181 return getSema().OpenMP().ActOnOpenMPDistScheduleClause(
2182 Kind
, ChunkSize
, StartLoc
, LParenLoc
, KindLoc
, CommaLoc
, EndLoc
);
2185 /// Build a new OpenMP 'to' clause.
2187 /// By default, performs semantic analysis to build the new statement.
2188 /// Subclasses may override this routine to provide different behavior.
2190 RebuildOMPToClause(ArrayRef
<OpenMPMotionModifierKind
> MotionModifiers
,
2191 ArrayRef
<SourceLocation
> MotionModifiersLoc
,
2192 CXXScopeSpec
&MapperIdScopeSpec
,
2193 DeclarationNameInfo
&MapperId
, SourceLocation ColonLoc
,
2194 ArrayRef
<Expr
*> VarList
, const OMPVarListLocTy
&Locs
,
2195 ArrayRef
<Expr
*> UnresolvedMappers
) {
2196 return getSema().OpenMP().ActOnOpenMPToClause(
2197 MotionModifiers
, MotionModifiersLoc
, MapperIdScopeSpec
, MapperId
,
2198 ColonLoc
, VarList
, Locs
, UnresolvedMappers
);
2201 /// Build a new OpenMP 'from' clause.
2203 /// By default, performs semantic analysis to build the new statement.
2204 /// Subclasses may override this routine to provide different behavior.
2206 RebuildOMPFromClause(ArrayRef
<OpenMPMotionModifierKind
> MotionModifiers
,
2207 ArrayRef
<SourceLocation
> MotionModifiersLoc
,
2208 CXXScopeSpec
&MapperIdScopeSpec
,
2209 DeclarationNameInfo
&MapperId
, SourceLocation ColonLoc
,
2210 ArrayRef
<Expr
*> VarList
, const OMPVarListLocTy
&Locs
,
2211 ArrayRef
<Expr
*> UnresolvedMappers
) {
2212 return getSema().OpenMP().ActOnOpenMPFromClause(
2213 MotionModifiers
, MotionModifiersLoc
, MapperIdScopeSpec
, MapperId
,
2214 ColonLoc
, VarList
, Locs
, UnresolvedMappers
);
2217 /// Build a new OpenMP 'use_device_ptr' clause.
2219 /// By default, performs semantic analysis to build the new OpenMP clause.
2220 /// Subclasses may override this routine to provide different behavior.
2221 OMPClause
*RebuildOMPUseDevicePtrClause(ArrayRef
<Expr
*> VarList
,
2222 const OMPVarListLocTy
&Locs
) {
2223 return getSema().OpenMP().ActOnOpenMPUseDevicePtrClause(VarList
, Locs
);
2226 /// Build a new OpenMP 'use_device_addr' clause.
2228 /// By default, performs semantic analysis to build the new OpenMP clause.
2229 /// Subclasses may override this routine to provide different behavior.
2230 OMPClause
*RebuildOMPUseDeviceAddrClause(ArrayRef
<Expr
*> VarList
,
2231 const OMPVarListLocTy
&Locs
) {
2232 return getSema().OpenMP().ActOnOpenMPUseDeviceAddrClause(VarList
, Locs
);
2235 /// Build a new OpenMP 'is_device_ptr' clause.
2237 /// By default, performs semantic analysis to build the new OpenMP clause.
2238 /// Subclasses may override this routine to provide different behavior.
2239 OMPClause
*RebuildOMPIsDevicePtrClause(ArrayRef
<Expr
*> VarList
,
2240 const OMPVarListLocTy
&Locs
) {
2241 return getSema().OpenMP().ActOnOpenMPIsDevicePtrClause(VarList
, Locs
);
2244 /// Build a new OpenMP 'has_device_addr' clause.
2246 /// By default, performs semantic analysis to build the new OpenMP clause.
2247 /// Subclasses may override this routine to provide different behavior.
2248 OMPClause
*RebuildOMPHasDeviceAddrClause(ArrayRef
<Expr
*> VarList
,
2249 const OMPVarListLocTy
&Locs
) {
2250 return getSema().OpenMP().ActOnOpenMPHasDeviceAddrClause(VarList
, Locs
);
2253 /// Build a new OpenMP 'defaultmap' clause.
2255 /// By default, performs semantic analysis to build the new OpenMP clause.
2256 /// Subclasses may override this routine to provide different behavior.
2257 OMPClause
*RebuildOMPDefaultmapClause(OpenMPDefaultmapClauseModifier M
,
2258 OpenMPDefaultmapClauseKind Kind
,
2259 SourceLocation StartLoc
,
2260 SourceLocation LParenLoc
,
2261 SourceLocation MLoc
,
2262 SourceLocation KindLoc
,
2263 SourceLocation EndLoc
) {
2264 return getSema().OpenMP().ActOnOpenMPDefaultmapClause(
2265 M
, Kind
, StartLoc
, LParenLoc
, MLoc
, KindLoc
, EndLoc
);
2268 /// Build a new OpenMP 'nontemporal' clause.
2270 /// By default, performs semantic analysis to build the new OpenMP clause.
2271 /// Subclasses may override this routine to provide different behavior.
2272 OMPClause
*RebuildOMPNontemporalClause(ArrayRef
<Expr
*> VarList
,
2273 SourceLocation StartLoc
,
2274 SourceLocation LParenLoc
,
2275 SourceLocation EndLoc
) {
2276 return getSema().OpenMP().ActOnOpenMPNontemporalClause(VarList
, StartLoc
,
2280 /// Build a new OpenMP 'inclusive' clause.
2282 /// By default, performs semantic analysis to build the new OpenMP clause.
2283 /// Subclasses may override this routine to provide different behavior.
2284 OMPClause
*RebuildOMPInclusiveClause(ArrayRef
<Expr
*> VarList
,
2285 SourceLocation StartLoc
,
2286 SourceLocation LParenLoc
,
2287 SourceLocation EndLoc
) {
2288 return getSema().OpenMP().ActOnOpenMPInclusiveClause(VarList
, StartLoc
,
2292 /// Build a new OpenMP 'exclusive' clause.
2294 /// By default, performs semantic analysis to build the new OpenMP clause.
2295 /// Subclasses may override this routine to provide different behavior.
2296 OMPClause
*RebuildOMPExclusiveClause(ArrayRef
<Expr
*> VarList
,
2297 SourceLocation StartLoc
,
2298 SourceLocation LParenLoc
,
2299 SourceLocation EndLoc
) {
2300 return getSema().OpenMP().ActOnOpenMPExclusiveClause(VarList
, StartLoc
,
2304 /// Build a new OpenMP 'uses_allocators' clause.
2306 /// By default, performs semantic analysis to build the new OpenMP clause.
2307 /// Subclasses may override this routine to provide different behavior.
2308 OMPClause
*RebuildOMPUsesAllocatorsClause(
2309 ArrayRef
<SemaOpenMP::UsesAllocatorsData
> Data
, SourceLocation StartLoc
,
2310 SourceLocation LParenLoc
, SourceLocation EndLoc
) {
2311 return getSema().OpenMP().ActOnOpenMPUsesAllocatorClause(
2312 StartLoc
, LParenLoc
, EndLoc
, Data
);
2315 /// Build a new OpenMP 'affinity' clause.
2317 /// By default, performs semantic analysis to build the new OpenMP clause.
2318 /// Subclasses may override this routine to provide different behavior.
2319 OMPClause
*RebuildOMPAffinityClause(SourceLocation StartLoc
,
2320 SourceLocation LParenLoc
,
2321 SourceLocation ColonLoc
,
2322 SourceLocation EndLoc
, Expr
*Modifier
,
2323 ArrayRef
<Expr
*> Locators
) {
2324 return getSema().OpenMP().ActOnOpenMPAffinityClause(
2325 StartLoc
, LParenLoc
, ColonLoc
, EndLoc
, Modifier
, Locators
);
2328 /// Build a new OpenMP 'order' clause.
2330 /// By default, performs semantic analysis to build the new OpenMP clause.
2331 /// Subclasses may override this routine to provide different behavior.
2332 OMPClause
*RebuildOMPOrderClause(
2333 OpenMPOrderClauseKind Kind
, SourceLocation KindKwLoc
,
2334 SourceLocation StartLoc
, SourceLocation LParenLoc
, SourceLocation EndLoc
,
2335 OpenMPOrderClauseModifier Modifier
, SourceLocation ModifierKwLoc
) {
2336 return getSema().OpenMP().ActOnOpenMPOrderClause(
2337 Modifier
, Kind
, StartLoc
, LParenLoc
, ModifierKwLoc
, KindKwLoc
, EndLoc
);
2340 /// Build a new OpenMP 'init' clause.
2342 /// By default, performs semantic analysis to build the new OpenMP clause.
2343 /// Subclasses may override this routine to provide different behavior.
2344 OMPClause
*RebuildOMPInitClause(Expr
*InteropVar
, OMPInteropInfo
&InteropInfo
,
2345 SourceLocation StartLoc
,
2346 SourceLocation LParenLoc
,
2347 SourceLocation VarLoc
,
2348 SourceLocation EndLoc
) {
2349 return getSema().OpenMP().ActOnOpenMPInitClause(
2350 InteropVar
, InteropInfo
, StartLoc
, LParenLoc
, VarLoc
, EndLoc
);
2353 /// Build a new OpenMP 'use' clause.
2355 /// By default, performs semantic analysis to build the new OpenMP clause.
2356 /// Subclasses may override this routine to provide different behavior.
2357 OMPClause
*RebuildOMPUseClause(Expr
*InteropVar
, SourceLocation StartLoc
,
2358 SourceLocation LParenLoc
,
2359 SourceLocation VarLoc
, SourceLocation EndLoc
) {
2360 return getSema().OpenMP().ActOnOpenMPUseClause(InteropVar
, StartLoc
,
2361 LParenLoc
, VarLoc
, EndLoc
);
2364 /// Build a new OpenMP 'destroy' clause.
2366 /// By default, performs semantic analysis to build the new OpenMP clause.
2367 /// Subclasses may override this routine to provide different behavior.
2368 OMPClause
*RebuildOMPDestroyClause(Expr
*InteropVar
, SourceLocation StartLoc
,
2369 SourceLocation LParenLoc
,
2370 SourceLocation VarLoc
,
2371 SourceLocation EndLoc
) {
2372 return getSema().OpenMP().ActOnOpenMPDestroyClause(
2373 InteropVar
, StartLoc
, LParenLoc
, VarLoc
, EndLoc
);
2376 /// Build a new OpenMP 'novariants' clause.
2378 /// By default, performs semantic analysis to build the new OpenMP clause.
2379 /// Subclasses may override this routine to provide different behavior.
2380 OMPClause
*RebuildOMPNovariantsClause(Expr
*Condition
,
2381 SourceLocation StartLoc
,
2382 SourceLocation LParenLoc
,
2383 SourceLocation EndLoc
) {
2384 return getSema().OpenMP().ActOnOpenMPNovariantsClause(Condition
, StartLoc
,
2388 /// Build a new OpenMP 'nocontext' clause.
2390 /// By default, performs semantic analysis to build the new OpenMP clause.
2391 /// Subclasses may override this routine to provide different behavior.
2392 OMPClause
*RebuildOMPNocontextClause(Expr
*Condition
, SourceLocation StartLoc
,
2393 SourceLocation LParenLoc
,
2394 SourceLocation EndLoc
) {
2395 return getSema().OpenMP().ActOnOpenMPNocontextClause(Condition
, StartLoc
,
2399 /// Build a new OpenMP 'filter' clause.
2401 /// By default, performs semantic analysis to build the new OpenMP clause.
2402 /// Subclasses may override this routine to provide different behavior.
2403 OMPClause
*RebuildOMPFilterClause(Expr
*ThreadID
, SourceLocation StartLoc
,
2404 SourceLocation LParenLoc
,
2405 SourceLocation EndLoc
) {
2406 return getSema().OpenMP().ActOnOpenMPFilterClause(ThreadID
, StartLoc
,
2410 /// Build a new OpenMP 'bind' clause.
2412 /// By default, performs semantic analysis to build the new OpenMP clause.
2413 /// Subclasses may override this routine to provide different behavior.
2414 OMPClause
*RebuildOMPBindClause(OpenMPBindClauseKind Kind
,
2415 SourceLocation KindLoc
,
2416 SourceLocation StartLoc
,
2417 SourceLocation LParenLoc
,
2418 SourceLocation EndLoc
) {
2419 return getSema().OpenMP().ActOnOpenMPBindClause(Kind
, KindLoc
, StartLoc
,
2423 /// Build a new OpenMP 'ompx_dyn_cgroup_mem' clause.
2425 /// By default, performs semantic analysis to build the new OpenMP clause.
2426 /// Subclasses may override this routine to provide different behavior.
2427 OMPClause
*RebuildOMPXDynCGroupMemClause(Expr
*Size
, SourceLocation StartLoc
,
2428 SourceLocation LParenLoc
,
2429 SourceLocation EndLoc
) {
2430 return getSema().OpenMP().ActOnOpenMPXDynCGroupMemClause(Size
, StartLoc
,
2434 /// Build a new OpenMP 'ompx_attribute' clause.
2436 /// By default, performs semantic analysis to build the new OpenMP clause.
2437 /// Subclasses may override this routine to provide different behavior.
2438 OMPClause
*RebuildOMPXAttributeClause(ArrayRef
<const Attr
*> Attrs
,
2439 SourceLocation StartLoc
,
2440 SourceLocation LParenLoc
,
2441 SourceLocation EndLoc
) {
2442 return getSema().OpenMP().ActOnOpenMPXAttributeClause(Attrs
, StartLoc
,
2446 /// Build a new OpenMP 'ompx_bare' clause.
2448 /// By default, performs semantic analysis to build the new OpenMP clause.
2449 /// Subclasses may override this routine to provide different behavior.
2450 OMPClause
*RebuildOMPXBareClause(SourceLocation StartLoc
,
2451 SourceLocation EndLoc
) {
2452 return getSema().OpenMP().ActOnOpenMPXBareClause(StartLoc
, EndLoc
);
2455 /// Build a new OpenMP 'align' clause.
2457 /// By default, performs semantic analysis to build the new OpenMP clause.
2458 /// Subclasses may override this routine to provide different behavior.
2459 OMPClause
*RebuildOMPAlignClause(Expr
*A
, SourceLocation StartLoc
,
2460 SourceLocation LParenLoc
,
2461 SourceLocation EndLoc
) {
2462 return getSema().OpenMP().ActOnOpenMPAlignClause(A
, StartLoc
, LParenLoc
,
2466 /// Build a new OpenMP 'at' clause.
2468 /// By default, performs semantic analysis to build the new OpenMP clause.
2469 /// Subclasses may override this routine to provide different behavior.
2470 OMPClause
*RebuildOMPAtClause(OpenMPAtClauseKind Kind
, SourceLocation KwLoc
,
2471 SourceLocation StartLoc
,
2472 SourceLocation LParenLoc
,
2473 SourceLocation EndLoc
) {
2474 return getSema().OpenMP().ActOnOpenMPAtClause(Kind
, KwLoc
, StartLoc
,
2478 /// Build a new OpenMP 'severity' clause.
2480 /// By default, performs semantic analysis to build the new OpenMP clause.
2481 /// Subclasses may override this routine to provide different behavior.
2482 OMPClause
*RebuildOMPSeverityClause(OpenMPSeverityClauseKind Kind
,
2483 SourceLocation KwLoc
,
2484 SourceLocation StartLoc
,
2485 SourceLocation LParenLoc
,
2486 SourceLocation EndLoc
) {
2487 return getSema().OpenMP().ActOnOpenMPSeverityClause(Kind
, KwLoc
, StartLoc
,
2491 /// Build a new OpenMP 'message' clause.
2493 /// By default, performs semantic analysis to build the new OpenMP clause.
2494 /// Subclasses may override this routine to provide different behavior.
2495 OMPClause
*RebuildOMPMessageClause(Expr
*MS
, SourceLocation StartLoc
,
2496 SourceLocation LParenLoc
,
2497 SourceLocation EndLoc
) {
2498 return getSema().OpenMP().ActOnOpenMPMessageClause(MS
, StartLoc
, LParenLoc
,
2502 /// Build a new OpenMP 'doacross' clause.
2504 /// By default, performs semantic analysis to build the new OpenMP clause.
2505 /// Subclasses may override this routine to provide different behavior.
2507 RebuildOMPDoacrossClause(OpenMPDoacrossClauseModifier DepType
,
2508 SourceLocation DepLoc
, SourceLocation ColonLoc
,
2509 ArrayRef
<Expr
*> VarList
, SourceLocation StartLoc
,
2510 SourceLocation LParenLoc
, SourceLocation EndLoc
) {
2511 return getSema().OpenMP().ActOnOpenMPDoacrossClause(
2512 DepType
, DepLoc
, ColonLoc
, VarList
, StartLoc
, LParenLoc
, EndLoc
);
2515 /// Build a new OpenMP 'holds' clause.
2516 OMPClause
*RebuildOMPHoldsClause(Expr
*A
, SourceLocation StartLoc
,
2517 SourceLocation LParenLoc
,
2518 SourceLocation EndLoc
) {
2519 return getSema().OpenMP().ActOnOpenMPHoldsClause(A
, StartLoc
, LParenLoc
,
2523 /// Rebuild the operand to an Objective-C \@synchronized statement.
2525 /// By default, performs semantic analysis to build the new statement.
2526 /// Subclasses may override this routine to provide different behavior.
2527 ExprResult
RebuildObjCAtSynchronizedOperand(SourceLocation atLoc
,
2529 return getSema().ObjC().ActOnObjCAtSynchronizedOperand(atLoc
, object
);
2532 /// Build a new Objective-C \@synchronized statement.
2534 /// By default, performs semantic analysis to build the new statement.
2535 /// Subclasses may override this routine to provide different behavior.
2536 StmtResult
RebuildObjCAtSynchronizedStmt(SourceLocation AtLoc
,
2537 Expr
*Object
, Stmt
*Body
) {
2538 return getSema().ObjC().ActOnObjCAtSynchronizedStmt(AtLoc
, Object
, Body
);
2541 /// Build a new Objective-C \@autoreleasepool statement.
2543 /// By default, performs semantic analysis to build the new statement.
2544 /// Subclasses may override this routine to provide different behavior.
2545 StmtResult
RebuildObjCAutoreleasePoolStmt(SourceLocation AtLoc
,
2547 return getSema().ObjC().ActOnObjCAutoreleasePoolStmt(AtLoc
, Body
);
2550 /// Build a new Objective-C fast enumeration statement.
2552 /// By default, performs semantic analysis to build the new statement.
2553 /// Subclasses may override this routine to provide different behavior.
2554 StmtResult
RebuildObjCForCollectionStmt(SourceLocation ForLoc
,
2557 SourceLocation RParenLoc
,
2559 StmtResult ForEachStmt
= getSema().ObjC().ActOnObjCForCollectionStmt(
2560 ForLoc
, Element
, Collection
, RParenLoc
);
2561 if (ForEachStmt
.isInvalid())
2564 return getSema().ObjC().FinishObjCForCollectionStmt(ForEachStmt
.get(),
2568 /// Build a new C++ exception declaration.
2570 /// By default, performs semantic analysis to build the new decaration.
2571 /// Subclasses may override this routine to provide different behavior.
2572 VarDecl
*RebuildExceptionDecl(VarDecl
*ExceptionDecl
,
2573 TypeSourceInfo
*Declarator
,
2574 SourceLocation StartLoc
,
2575 SourceLocation IdLoc
,
2576 IdentifierInfo
*Id
) {
2577 VarDecl
*Var
= getSema().BuildExceptionDeclaration(nullptr, Declarator
,
2578 StartLoc
, IdLoc
, Id
);
2580 getSema().CurContext
->addDecl(Var
);
2584 /// Build a new C++ catch statement.
2586 /// By default, performs semantic analysis to build the new statement.
2587 /// Subclasses may override this routine to provide different behavior.
2588 StmtResult
RebuildCXXCatchStmt(SourceLocation CatchLoc
,
2589 VarDecl
*ExceptionDecl
,
2591 return Owned(new (getSema().Context
) CXXCatchStmt(CatchLoc
, ExceptionDecl
,
2595 /// Build a new C++ try statement.
2597 /// By default, performs semantic analysis to build the new statement.
2598 /// Subclasses may override this routine to provide different behavior.
2599 StmtResult
RebuildCXXTryStmt(SourceLocation TryLoc
, Stmt
*TryBlock
,
2600 ArrayRef
<Stmt
*> Handlers
) {
2601 return getSema().ActOnCXXTryBlock(TryLoc
, TryBlock
, Handlers
);
2604 /// Build a new C++0x range-based for statement.
2606 /// By default, performs semantic analysis to build the new statement.
2607 /// Subclasses may override this routine to provide different behavior.
2608 StmtResult
RebuildCXXForRangeStmt(
2609 SourceLocation ForLoc
, SourceLocation CoawaitLoc
, Stmt
*Init
,
2610 SourceLocation ColonLoc
, Stmt
*Range
, Stmt
*Begin
, Stmt
*End
, Expr
*Cond
,
2611 Expr
*Inc
, Stmt
*LoopVar
, SourceLocation RParenLoc
,
2612 ArrayRef
<MaterializeTemporaryExpr
*> LifetimeExtendTemps
) {
2613 // If we've just learned that the range is actually an Objective-C
2614 // collection, treat this as an Objective-C fast enumeration loop.
2615 if (DeclStmt
*RangeStmt
= dyn_cast
<DeclStmt
>(Range
)) {
2616 if (RangeStmt
->isSingleDecl()) {
2617 if (VarDecl
*RangeVar
= dyn_cast
<VarDecl
>(RangeStmt
->getSingleDecl())) {
2618 if (RangeVar
->isInvalidDecl())
2621 Expr
*RangeExpr
= RangeVar
->getInit();
2622 if (!RangeExpr
->isTypeDependent() &&
2623 RangeExpr
->getType()->isObjCObjectPointerType()) {
2624 // FIXME: Support init-statements in Objective-C++20 ranged for
2627 return SemaRef
.Diag(Init
->getBeginLoc(),
2628 diag::err_objc_for_range_init_stmt
)
2629 << Init
->getSourceRange();
2631 return getSema().ObjC().ActOnObjCForCollectionStmt(
2632 ForLoc
, LoopVar
, RangeExpr
, RParenLoc
);
2638 return getSema().BuildCXXForRangeStmt(
2639 ForLoc
, CoawaitLoc
, Init
, ColonLoc
, Range
, Begin
, End
, Cond
, Inc
,
2640 LoopVar
, RParenLoc
, Sema::BFRK_Rebuild
, LifetimeExtendTemps
);
2643 /// Build a new C++0x range-based for statement.
2645 /// By default, performs semantic analysis to build the new statement.
2646 /// Subclasses may override this routine to provide different behavior.
2647 StmtResult
RebuildMSDependentExistsStmt(SourceLocation KeywordLoc
,
2649 NestedNameSpecifierLoc QualifierLoc
,
2650 DeclarationNameInfo NameInfo
,
2652 return getSema().BuildMSDependentExistsStmt(KeywordLoc
, IsIfExists
,
2653 QualifierLoc
, NameInfo
, Nested
);
2656 /// Attach body to a C++0x range-based for statement.
2658 /// By default, performs semantic analysis to finish the new statement.
2659 /// Subclasses may override this routine to provide different behavior.
2660 StmtResult
FinishCXXForRangeStmt(Stmt
*ForRange
, Stmt
*Body
) {
2661 return getSema().FinishCXXForRangeStmt(ForRange
, Body
);
2664 StmtResult
RebuildSEHTryStmt(bool IsCXXTry
, SourceLocation TryLoc
,
2665 Stmt
*TryBlock
, Stmt
*Handler
) {
2666 return getSema().ActOnSEHTryBlock(IsCXXTry
, TryLoc
, TryBlock
, Handler
);
2669 StmtResult
RebuildSEHExceptStmt(SourceLocation Loc
, Expr
*FilterExpr
,
2671 return getSema().ActOnSEHExceptBlock(Loc
, FilterExpr
, Block
);
2674 StmtResult
RebuildSEHFinallyStmt(SourceLocation Loc
, Stmt
*Block
) {
2675 return SEHFinallyStmt::Create(getSema().getASTContext(), Loc
, Block
);
2678 ExprResult
RebuildSYCLUniqueStableNameExpr(SourceLocation OpLoc
,
2679 SourceLocation LParen
,
2680 SourceLocation RParen
,
2681 TypeSourceInfo
*TSI
) {
2682 return getSema().SYCL().BuildUniqueStableNameExpr(OpLoc
, LParen
, RParen
,
2686 /// Build a new predefined expression.
2688 /// By default, performs semantic analysis to build the new expression.
2689 /// Subclasses may override this routine to provide different behavior.
2690 ExprResult
RebuildPredefinedExpr(SourceLocation Loc
, PredefinedIdentKind IK
) {
2691 return getSema().BuildPredefinedExpr(Loc
, IK
);
2694 /// Build a new expression that references a declaration.
2696 /// By default, performs semantic analysis to build the new expression.
2697 /// Subclasses may override this routine to provide different behavior.
2698 ExprResult
RebuildDeclarationNameExpr(const CXXScopeSpec
&SS
,
2701 return getSema().BuildDeclarationNameExpr(SS
, R
, RequiresADL
);
2705 /// Build a new expression that references a declaration.
2707 /// By default, performs semantic analysis to build the new expression.
2708 /// Subclasses may override this routine to provide different behavior.
2709 ExprResult
RebuildDeclRefExpr(NestedNameSpecifierLoc QualifierLoc
,
2711 const DeclarationNameInfo
&NameInfo
,
2713 TemplateArgumentListInfo
*TemplateArgs
) {
2715 SS
.Adopt(QualifierLoc
);
2716 return getSema().BuildDeclarationNameExpr(SS
, NameInfo
, VD
, Found
,
2720 /// Build a new expression in parentheses.
2722 /// By default, performs semantic analysis to build the new expression.
2723 /// Subclasses may override this routine to provide different behavior.
2724 ExprResult
RebuildParenExpr(Expr
*SubExpr
, SourceLocation LParen
,
2725 SourceLocation RParen
) {
2726 return getSema().ActOnParenExpr(LParen
, RParen
, SubExpr
);
2729 /// Build a new pseudo-destructor expression.
2731 /// By default, performs semantic analysis to build the new expression.
2732 /// Subclasses may override this routine to provide different behavior.
2733 ExprResult
RebuildCXXPseudoDestructorExpr(Expr
*Base
,
2734 SourceLocation OperatorLoc
,
2737 TypeSourceInfo
*ScopeType
,
2738 SourceLocation CCLoc
,
2739 SourceLocation TildeLoc
,
2740 PseudoDestructorTypeStorage Destroyed
);
2742 /// Build a new unary operator expression.
2744 /// By default, performs semantic analysis to build the new expression.
2745 /// Subclasses may override this routine to provide different behavior.
2746 ExprResult
RebuildUnaryOperator(SourceLocation OpLoc
,
2747 UnaryOperatorKind Opc
,
2749 return getSema().BuildUnaryOp(/*Scope=*/nullptr, OpLoc
, Opc
, SubExpr
);
2752 /// Build a new builtin offsetof expression.
2754 /// By default, performs semantic analysis to build the new expression.
2755 /// Subclasses may override this routine to provide different behavior.
2756 ExprResult
RebuildOffsetOfExpr(SourceLocation OperatorLoc
,
2757 TypeSourceInfo
*Type
,
2758 ArrayRef
<Sema::OffsetOfComponent
> Components
,
2759 SourceLocation RParenLoc
) {
2760 return getSema().BuildBuiltinOffsetOf(OperatorLoc
, Type
, Components
,
2764 /// Build a new sizeof, alignof or vec_step expression with a
2767 /// By default, performs semantic analysis to build the new expression.
2768 /// Subclasses may override this routine to provide different behavior.
2769 ExprResult
RebuildUnaryExprOrTypeTrait(TypeSourceInfo
*TInfo
,
2770 SourceLocation OpLoc
,
2771 UnaryExprOrTypeTrait ExprKind
,
2773 return getSema().CreateUnaryExprOrTypeTraitExpr(TInfo
, OpLoc
, ExprKind
, R
);
2776 /// Build a new sizeof, alignof or vec step expression with an
2777 /// expression argument.
2779 /// By default, performs semantic analysis to build the new expression.
2780 /// Subclasses may override this routine to provide different behavior.
2781 ExprResult
RebuildUnaryExprOrTypeTrait(Expr
*SubExpr
, SourceLocation OpLoc
,
2782 UnaryExprOrTypeTrait ExprKind
,
2785 = getSema().CreateUnaryExprOrTypeTraitExpr(SubExpr
, OpLoc
, ExprKind
);
2786 if (Result
.isInvalid())
2792 /// Build a new array subscript expression.
2794 /// By default, performs semantic analysis to build the new expression.
2795 /// Subclasses may override this routine to provide different behavior.
2796 ExprResult
RebuildArraySubscriptExpr(Expr
*LHS
,
2797 SourceLocation LBracketLoc
,
2799 SourceLocation RBracketLoc
) {
2800 return getSema().ActOnArraySubscriptExpr(/*Scope=*/nullptr, LHS
,
2805 /// Build a new matrix subscript expression.
2807 /// By default, performs semantic analysis to build the new expression.
2808 /// Subclasses may override this routine to provide different behavior.
2809 ExprResult
RebuildMatrixSubscriptExpr(Expr
*Base
, Expr
*RowIdx
,
2811 SourceLocation RBracketLoc
) {
2812 return getSema().CreateBuiltinMatrixSubscriptExpr(Base
, RowIdx
, ColumnIdx
,
2816 /// Build a new array section expression.
2818 /// By default, performs semantic analysis to build the new expression.
2819 /// Subclasses may override this routine to provide different behavior.
2820 ExprResult
RebuildArraySectionExpr(bool IsOMPArraySection
, Expr
*Base
,
2821 SourceLocation LBracketLoc
,
2823 SourceLocation ColonLocFirst
,
2824 SourceLocation ColonLocSecond
,
2825 Expr
*Length
, Expr
*Stride
,
2826 SourceLocation RBracketLoc
) {
2827 if (IsOMPArraySection
)
2828 return getSema().OpenMP().ActOnOMPArraySectionExpr(
2829 Base
, LBracketLoc
, LowerBound
, ColonLocFirst
, ColonLocSecond
, Length
,
2830 Stride
, RBracketLoc
);
2832 assert(Stride
== nullptr && !ColonLocSecond
.isValid() &&
2833 "Stride/second colon not allowed for OpenACC");
2835 return getSema().OpenACC().ActOnArraySectionExpr(
2836 Base
, LBracketLoc
, LowerBound
, ColonLocFirst
, Length
, RBracketLoc
);
2839 /// Build a new array shaping expression.
2841 /// By default, performs semantic analysis to build the new expression.
2842 /// Subclasses may override this routine to provide different behavior.
2843 ExprResult
RebuildOMPArrayShapingExpr(Expr
*Base
, SourceLocation LParenLoc
,
2844 SourceLocation RParenLoc
,
2845 ArrayRef
<Expr
*> Dims
,
2846 ArrayRef
<SourceRange
> BracketsRanges
) {
2847 return getSema().OpenMP().ActOnOMPArrayShapingExpr(
2848 Base
, LParenLoc
, RParenLoc
, Dims
, BracketsRanges
);
2851 /// Build a new iterator expression.
2853 /// By default, performs semantic analysis to build the new expression.
2854 /// Subclasses may override this routine to provide different behavior.
2856 RebuildOMPIteratorExpr(SourceLocation IteratorKwLoc
, SourceLocation LLoc
,
2857 SourceLocation RLoc
,
2858 ArrayRef
<SemaOpenMP::OMPIteratorData
> Data
) {
2859 return getSema().OpenMP().ActOnOMPIteratorExpr(
2860 /*Scope=*/nullptr, IteratorKwLoc
, LLoc
, RLoc
, Data
);
2863 /// Build a new call expression.
2865 /// By default, performs semantic analysis to build the new expression.
2866 /// Subclasses may override this routine to provide different behavior.
2867 ExprResult
RebuildCallExpr(Expr
*Callee
, SourceLocation LParenLoc
,
2869 SourceLocation RParenLoc
,
2870 Expr
*ExecConfig
= nullptr) {
2871 return getSema().ActOnCallExpr(
2872 /*Scope=*/nullptr, Callee
, LParenLoc
, Args
, RParenLoc
, ExecConfig
);
2875 ExprResult
RebuildCxxSubscriptExpr(Expr
*Callee
, SourceLocation LParenLoc
,
2877 SourceLocation RParenLoc
) {
2878 return getSema().ActOnArraySubscriptExpr(
2879 /*Scope=*/nullptr, Callee
, LParenLoc
, Args
, RParenLoc
);
2882 /// Build a new member access expression.
2884 /// By default, performs semantic analysis to build the new expression.
2885 /// Subclasses may override this routine to provide different behavior.
2886 ExprResult
RebuildMemberExpr(Expr
*Base
, SourceLocation OpLoc
,
2888 NestedNameSpecifierLoc QualifierLoc
,
2889 SourceLocation TemplateKWLoc
,
2890 const DeclarationNameInfo
&MemberNameInfo
,
2892 NamedDecl
*FoundDecl
,
2893 const TemplateArgumentListInfo
*ExplicitTemplateArgs
,
2894 NamedDecl
*FirstQualifierInScope
) {
2895 ExprResult BaseResult
= getSema().PerformMemberExprBaseConversion(Base
,
2897 if (!Member
->getDeclName()) {
2898 // We have a reference to an unnamed field. This is always the
2899 // base of an anonymous struct/union member access, i.e. the
2900 // field is always of record type.
2901 assert(Member
->getType()->isRecordType() &&
2902 "unnamed member not of record type?");
2905 getSema().PerformObjectMemberConversion(BaseResult
.get(),
2906 QualifierLoc
.getNestedNameSpecifier(),
2908 if (BaseResult
.isInvalid())
2910 Base
= BaseResult
.get();
2912 // `TranformMaterializeTemporaryExpr()` removes materialized temporaries
2913 // from the AST, so we need to re-insert them if needed (since
2914 // `BuildFieldRefereneExpr()` doesn't do this).
2915 if (!isArrow
&& Base
->isPRValue()) {
2916 BaseResult
= getSema().TemporaryMaterializationConversion(Base
);
2917 if (BaseResult
.isInvalid())
2919 Base
= BaseResult
.get();
2922 CXXScopeSpec EmptySS
;
2923 return getSema().BuildFieldReferenceExpr(
2924 Base
, isArrow
, OpLoc
, EmptySS
, cast
<FieldDecl
>(Member
),
2925 DeclAccessPair::make(FoundDecl
, FoundDecl
->getAccess()),
2930 SS
.Adopt(QualifierLoc
);
2932 Base
= BaseResult
.get();
2933 if (Base
->containsErrors())
2936 QualType BaseType
= Base
->getType();
2938 if (isArrow
&& !BaseType
->isPointerType())
2941 // FIXME: this involves duplicating earlier analysis in a lot of
2942 // cases; we should avoid this when possible.
2943 LookupResult
R(getSema(), MemberNameInfo
, Sema::LookupMemberName
);
2944 R
.addDecl(FoundDecl
);
2947 if (getSema().isUnevaluatedContext() && Base
->isImplicitCXXThis() &&
2948 isa
<FieldDecl
, IndirectFieldDecl
, MSPropertyDecl
>(Member
)) {
2949 if (auto *ThisClass
= cast
<CXXThisExpr
>(Base
)
2952 ->getAsCXXRecordDecl()) {
2953 auto *Class
= cast
<CXXRecordDecl
>(Member
->getDeclContext());
2954 // In unevaluated contexts, an expression supposed to be a member access
2955 // might reference a member in an unrelated class.
2956 if (!ThisClass
->Equals(Class
) && !ThisClass
->isDerivedFrom(Class
))
2957 return getSema().BuildDeclRefExpr(Member
, Member
->getType(),
2958 VK_LValue
, Member
->getLocation());
2962 return getSema().BuildMemberReferenceExpr(Base
, BaseType
, OpLoc
, isArrow
,
2964 FirstQualifierInScope
,
2965 R
, ExplicitTemplateArgs
,
2969 /// Build a new binary operator expression.
2971 /// By default, performs semantic analysis to build the new expression.
2972 /// Subclasses may override this routine to provide different behavior.
2973 ExprResult
RebuildBinaryOperator(SourceLocation OpLoc
,
2974 BinaryOperatorKind Opc
,
2975 Expr
*LHS
, Expr
*RHS
) {
2976 return getSema().BuildBinOp(/*Scope=*/nullptr, OpLoc
, Opc
, LHS
, RHS
);
2979 /// Build a new rewritten operator expression.
2981 /// By default, performs semantic analysis to build the new expression.
2982 /// Subclasses may override this routine to provide different behavior.
2983 ExprResult
RebuildCXXRewrittenBinaryOperator(
2984 SourceLocation OpLoc
, BinaryOperatorKind Opcode
,
2985 const UnresolvedSetImpl
&UnqualLookups
, Expr
*LHS
, Expr
*RHS
) {
2986 return getSema().CreateOverloadedBinOp(OpLoc
, Opcode
, UnqualLookups
, LHS
,
2987 RHS
, /*RequiresADL*/false);
2990 /// Build a new conditional operator expression.
2992 /// By default, performs semantic analysis to build the new expression.
2993 /// Subclasses may override this routine to provide different behavior.
2994 ExprResult
RebuildConditionalOperator(Expr
*Cond
,
2995 SourceLocation QuestionLoc
,
2997 SourceLocation ColonLoc
,
2999 return getSema().ActOnConditionalOp(QuestionLoc
, ColonLoc
, Cond
,
3003 /// Build a new C-style cast expression.
3005 /// By default, performs semantic analysis to build the new expression.
3006 /// Subclasses may override this routine to provide different behavior.
3007 ExprResult
RebuildCStyleCastExpr(SourceLocation LParenLoc
,
3008 TypeSourceInfo
*TInfo
,
3009 SourceLocation RParenLoc
,
3011 return getSema().BuildCStyleCastExpr(LParenLoc
, TInfo
, RParenLoc
,
3015 /// Build a new compound literal expression.
3017 /// By default, performs semantic analysis to build the new expression.
3018 /// Subclasses may override this routine to provide different behavior.
3019 ExprResult
RebuildCompoundLiteralExpr(SourceLocation LParenLoc
,
3020 TypeSourceInfo
*TInfo
,
3021 SourceLocation RParenLoc
,
3023 return getSema().BuildCompoundLiteralExpr(LParenLoc
, TInfo
, RParenLoc
,
3027 /// Build a new extended vector element access expression.
3029 /// By default, performs semantic analysis to build the new expression.
3030 /// Subclasses may override this routine to provide different behavior.
3031 ExprResult
RebuildExtVectorElementExpr(Expr
*Base
, SourceLocation OpLoc
,
3033 SourceLocation AccessorLoc
,
3034 IdentifierInfo
&Accessor
) {
3037 DeclarationNameInfo
NameInfo(&Accessor
, AccessorLoc
);
3038 return getSema().BuildMemberReferenceExpr(
3039 Base
, Base
->getType(), OpLoc
, IsArrow
, SS
, SourceLocation(),
3040 /*FirstQualifierInScope*/ nullptr, NameInfo
,
3041 /* TemplateArgs */ nullptr,
3045 /// Build a new initializer list expression.
3047 /// By default, performs semantic analysis to build the new expression.
3048 /// Subclasses may override this routine to provide different behavior.
3049 ExprResult
RebuildInitList(SourceLocation LBraceLoc
,
3051 SourceLocation RBraceLoc
) {
3052 return SemaRef
.BuildInitList(LBraceLoc
, Inits
, RBraceLoc
);
3055 /// Build a new designated initializer expression.
3057 /// By default, performs semantic analysis to build the new expression.
3058 /// Subclasses may override this routine to provide different behavior.
3059 ExprResult
RebuildDesignatedInitExpr(Designation
&Desig
,
3060 MultiExprArg ArrayExprs
,
3061 SourceLocation EqualOrColonLoc
,
3065 = SemaRef
.ActOnDesignatedInitializer(Desig
, EqualOrColonLoc
, GNUSyntax
,
3067 if (Result
.isInvalid())
3073 /// Build a new value-initialized expression.
3075 /// By default, builds the implicit value initialization without performing
3076 /// any semantic analysis. Subclasses may override this routine to provide
3077 /// different behavior.
3078 ExprResult
RebuildImplicitValueInitExpr(QualType T
) {
3079 return new (SemaRef
.Context
) ImplicitValueInitExpr(T
);
3082 /// Build a new \c va_arg expression.
3084 /// By default, performs semantic analysis to build the new expression.
3085 /// Subclasses may override this routine to provide different behavior.
3086 ExprResult
RebuildVAArgExpr(SourceLocation BuiltinLoc
,
3087 Expr
*SubExpr
, TypeSourceInfo
*TInfo
,
3088 SourceLocation RParenLoc
) {
3089 return getSema().BuildVAArgExpr(BuiltinLoc
,
3094 /// Build a new expression list in parentheses.
3096 /// By default, performs semantic analysis to build the new expression.
3097 /// Subclasses may override this routine to provide different behavior.
3098 ExprResult
RebuildParenListExpr(SourceLocation LParenLoc
,
3099 MultiExprArg SubExprs
,
3100 SourceLocation RParenLoc
) {
3101 return getSema().ActOnParenListExpr(LParenLoc
, RParenLoc
, SubExprs
);
3104 /// Build a new address-of-label expression.
3106 /// By default, performs semantic analysis, using the name of the label
3107 /// rather than attempting to map the label statement itself.
3108 /// Subclasses may override this routine to provide different behavior.
3109 ExprResult
RebuildAddrLabelExpr(SourceLocation AmpAmpLoc
,
3110 SourceLocation LabelLoc
, LabelDecl
*Label
) {
3111 return getSema().ActOnAddrLabel(AmpAmpLoc
, LabelLoc
, Label
);
3114 /// Build a new GNU statement expression.
3116 /// By default, performs semantic analysis to build the new expression.
3117 /// Subclasses may override this routine to provide different behavior.
3118 ExprResult
RebuildStmtExpr(SourceLocation LParenLoc
, Stmt
*SubStmt
,
3119 SourceLocation RParenLoc
, unsigned TemplateDepth
) {
3120 return getSema().BuildStmtExpr(LParenLoc
, SubStmt
, RParenLoc
,
3124 /// Build a new __builtin_choose_expr expression.
3126 /// By default, performs semantic analysis to build the new expression.
3127 /// Subclasses may override this routine to provide different behavior.
3128 ExprResult
RebuildChooseExpr(SourceLocation BuiltinLoc
,
3129 Expr
*Cond
, Expr
*LHS
, Expr
*RHS
,
3130 SourceLocation RParenLoc
) {
3131 return SemaRef
.ActOnChooseExpr(BuiltinLoc
,
3136 /// Build a new generic selection expression with an expression predicate.
3138 /// By default, performs semantic analysis to build the new expression.
3139 /// Subclasses may override this routine to provide different behavior.
3140 ExprResult
RebuildGenericSelectionExpr(SourceLocation KeyLoc
,
3141 SourceLocation DefaultLoc
,
3142 SourceLocation RParenLoc
,
3143 Expr
*ControllingExpr
,
3144 ArrayRef
<TypeSourceInfo
*> Types
,
3145 ArrayRef
<Expr
*> Exprs
) {
3146 return getSema().CreateGenericSelectionExpr(KeyLoc
, DefaultLoc
, RParenLoc
,
3147 /*PredicateIsExpr=*/true,
3148 ControllingExpr
, Types
, Exprs
);
3151 /// Build a new generic selection expression with a type predicate.
3153 /// By default, performs semantic analysis to build the new expression.
3154 /// Subclasses may override this routine to provide different behavior.
3155 ExprResult
RebuildGenericSelectionExpr(SourceLocation KeyLoc
,
3156 SourceLocation DefaultLoc
,
3157 SourceLocation RParenLoc
,
3158 TypeSourceInfo
*ControllingType
,
3159 ArrayRef
<TypeSourceInfo
*> Types
,
3160 ArrayRef
<Expr
*> Exprs
) {
3161 return getSema().CreateGenericSelectionExpr(KeyLoc
, DefaultLoc
, RParenLoc
,
3162 /*PredicateIsExpr=*/false,
3163 ControllingType
, Types
, Exprs
);
3166 /// Build a new overloaded operator call expression.
3168 /// By default, performs semantic analysis to build the new expression.
3169 /// The semantic analysis provides the behavior of template instantiation,
3170 /// copying with transformations that turn what looks like an overloaded
3171 /// operator call into a use of a builtin operator, performing
3172 /// argument-dependent lookup, etc. Subclasses may override this routine to
3173 /// provide different behavior.
3174 ExprResult
RebuildCXXOperatorCallExpr(OverloadedOperatorKind Op
,
3175 SourceLocation OpLoc
,
3176 SourceLocation CalleeLoc
,
3178 const UnresolvedSetImpl
&Functions
,
3179 Expr
*First
, Expr
*Second
);
3181 /// Build a new C++ "named" cast expression, such as static_cast or
3182 /// reinterpret_cast.
3184 /// By default, this routine dispatches to one of the more-specific routines
3185 /// for a particular named case, e.g., RebuildCXXStaticCastExpr().
3186 /// Subclasses may override this routine to provide different behavior.
3187 ExprResult
RebuildCXXNamedCastExpr(SourceLocation OpLoc
,
3188 Stmt::StmtClass Class
,
3189 SourceLocation LAngleLoc
,
3190 TypeSourceInfo
*TInfo
,
3191 SourceLocation RAngleLoc
,
3192 SourceLocation LParenLoc
,
3194 SourceLocation RParenLoc
) {
3196 case Stmt::CXXStaticCastExprClass
:
3197 return getDerived().RebuildCXXStaticCastExpr(OpLoc
, LAngleLoc
, TInfo
,
3198 RAngleLoc
, LParenLoc
,
3199 SubExpr
, RParenLoc
);
3201 case Stmt::CXXDynamicCastExprClass
:
3202 return getDerived().RebuildCXXDynamicCastExpr(OpLoc
, LAngleLoc
, TInfo
,
3203 RAngleLoc
, LParenLoc
,
3204 SubExpr
, RParenLoc
);
3206 case Stmt::CXXReinterpretCastExprClass
:
3207 return getDerived().RebuildCXXReinterpretCastExpr(OpLoc
, LAngleLoc
, TInfo
,
3208 RAngleLoc
, LParenLoc
,
3212 case Stmt::CXXConstCastExprClass
:
3213 return getDerived().RebuildCXXConstCastExpr(OpLoc
, LAngleLoc
, TInfo
,
3214 RAngleLoc
, LParenLoc
,
3215 SubExpr
, RParenLoc
);
3217 case Stmt::CXXAddrspaceCastExprClass
:
3218 return getDerived().RebuildCXXAddrspaceCastExpr(
3219 OpLoc
, LAngleLoc
, TInfo
, RAngleLoc
, LParenLoc
, SubExpr
, RParenLoc
);
3222 llvm_unreachable("Invalid C++ named cast");
3226 /// Build a new C++ static_cast expression.
3228 /// By default, performs semantic analysis to build the new expression.
3229 /// Subclasses may override this routine to provide different behavior.
3230 ExprResult
RebuildCXXStaticCastExpr(SourceLocation OpLoc
,
3231 SourceLocation LAngleLoc
,
3232 TypeSourceInfo
*TInfo
,
3233 SourceLocation RAngleLoc
,
3234 SourceLocation LParenLoc
,
3236 SourceLocation RParenLoc
) {
3237 return getSema().BuildCXXNamedCast(OpLoc
, tok::kw_static_cast
,
3239 SourceRange(LAngleLoc
, RAngleLoc
),
3240 SourceRange(LParenLoc
, RParenLoc
));
3243 /// Build a new C++ dynamic_cast expression.
3245 /// By default, performs semantic analysis to build the new expression.
3246 /// Subclasses may override this routine to provide different behavior.
3247 ExprResult
RebuildCXXDynamicCastExpr(SourceLocation OpLoc
,
3248 SourceLocation LAngleLoc
,
3249 TypeSourceInfo
*TInfo
,
3250 SourceLocation RAngleLoc
,
3251 SourceLocation LParenLoc
,
3253 SourceLocation RParenLoc
) {
3254 return getSema().BuildCXXNamedCast(OpLoc
, tok::kw_dynamic_cast
,
3256 SourceRange(LAngleLoc
, RAngleLoc
),
3257 SourceRange(LParenLoc
, RParenLoc
));
3260 /// Build a new C++ reinterpret_cast expression.
3262 /// By default, performs semantic analysis to build the new expression.
3263 /// Subclasses may override this routine to provide different behavior.
3264 ExprResult
RebuildCXXReinterpretCastExpr(SourceLocation OpLoc
,
3265 SourceLocation LAngleLoc
,
3266 TypeSourceInfo
*TInfo
,
3267 SourceLocation RAngleLoc
,
3268 SourceLocation LParenLoc
,
3270 SourceLocation RParenLoc
) {
3271 return getSema().BuildCXXNamedCast(OpLoc
, tok::kw_reinterpret_cast
,
3273 SourceRange(LAngleLoc
, RAngleLoc
),
3274 SourceRange(LParenLoc
, RParenLoc
));
3277 /// Build a new C++ const_cast expression.
3279 /// By default, performs semantic analysis to build the new expression.
3280 /// Subclasses may override this routine to provide different behavior.
3281 ExprResult
RebuildCXXConstCastExpr(SourceLocation OpLoc
,
3282 SourceLocation LAngleLoc
,
3283 TypeSourceInfo
*TInfo
,
3284 SourceLocation RAngleLoc
,
3285 SourceLocation LParenLoc
,
3287 SourceLocation RParenLoc
) {
3288 return getSema().BuildCXXNamedCast(OpLoc
, tok::kw_const_cast
,
3290 SourceRange(LAngleLoc
, RAngleLoc
),
3291 SourceRange(LParenLoc
, RParenLoc
));
3295 RebuildCXXAddrspaceCastExpr(SourceLocation OpLoc
, SourceLocation LAngleLoc
,
3296 TypeSourceInfo
*TInfo
, SourceLocation RAngleLoc
,
3297 SourceLocation LParenLoc
, Expr
*SubExpr
,
3298 SourceLocation RParenLoc
) {
3299 return getSema().BuildCXXNamedCast(
3300 OpLoc
, tok::kw_addrspace_cast
, TInfo
, SubExpr
,
3301 SourceRange(LAngleLoc
, RAngleLoc
), SourceRange(LParenLoc
, RParenLoc
));
3304 /// Build a new C++ functional-style cast expression.
3306 /// By default, performs semantic analysis to build the new expression.
3307 /// Subclasses may override this routine to provide different behavior.
3308 ExprResult
RebuildCXXFunctionalCastExpr(TypeSourceInfo
*TInfo
,
3309 SourceLocation LParenLoc
,
3311 SourceLocation RParenLoc
,
3312 bool ListInitialization
) {
3313 // If Sub is a ParenListExpr, then Sub is the syntatic form of a
3314 // CXXParenListInitExpr. Pass its expanded arguments so that the
3315 // CXXParenListInitExpr can be rebuilt.
3316 if (auto *PLE
= dyn_cast
<ParenListExpr
>(Sub
))
3317 return getSema().BuildCXXTypeConstructExpr(
3318 TInfo
, LParenLoc
, MultiExprArg(PLE
->getExprs(), PLE
->getNumExprs()),
3319 RParenLoc
, ListInitialization
);
3320 return getSema().BuildCXXTypeConstructExpr(TInfo
, LParenLoc
,
3321 MultiExprArg(&Sub
, 1), RParenLoc
,
3322 ListInitialization
);
3325 /// Build a new C++ __builtin_bit_cast expression.
3327 /// By default, performs semantic analysis to build the new expression.
3328 /// Subclasses may override this routine to provide different behavior.
3329 ExprResult
RebuildBuiltinBitCastExpr(SourceLocation KWLoc
,
3330 TypeSourceInfo
*TSI
, Expr
*Sub
,
3331 SourceLocation RParenLoc
) {
3332 return getSema().BuildBuiltinBitCastExpr(KWLoc
, TSI
, Sub
, RParenLoc
);
3335 /// Build a new C++ typeid(type) expression.
3337 /// By default, performs semantic analysis to build the new expression.
3338 /// Subclasses may override this routine to provide different behavior.
3339 ExprResult
RebuildCXXTypeidExpr(QualType TypeInfoType
,
3340 SourceLocation TypeidLoc
,
3341 TypeSourceInfo
*Operand
,
3342 SourceLocation RParenLoc
) {
3343 return getSema().BuildCXXTypeId(TypeInfoType
, TypeidLoc
, Operand
,
3348 /// Build a new C++ typeid(expr) expression.
3350 /// By default, performs semantic analysis to build the new expression.
3351 /// Subclasses may override this routine to provide different behavior.
3352 ExprResult
RebuildCXXTypeidExpr(QualType TypeInfoType
,
3353 SourceLocation TypeidLoc
,
3355 SourceLocation RParenLoc
) {
3356 return getSema().BuildCXXTypeId(TypeInfoType
, TypeidLoc
, Operand
,
3360 /// Build a new C++ __uuidof(type) expression.
3362 /// By default, performs semantic analysis to build the new expression.
3363 /// Subclasses may override this routine to provide different behavior.
3364 ExprResult
RebuildCXXUuidofExpr(QualType Type
, SourceLocation TypeidLoc
,
3365 TypeSourceInfo
*Operand
,
3366 SourceLocation RParenLoc
) {
3367 return getSema().BuildCXXUuidof(Type
, TypeidLoc
, Operand
, RParenLoc
);
3370 /// Build a new C++ __uuidof(expr) expression.
3372 /// By default, performs semantic analysis to build the new expression.
3373 /// Subclasses may override this routine to provide different behavior.
3374 ExprResult
RebuildCXXUuidofExpr(QualType Type
, SourceLocation TypeidLoc
,
3375 Expr
*Operand
, SourceLocation RParenLoc
) {
3376 return getSema().BuildCXXUuidof(Type
, TypeidLoc
, Operand
, RParenLoc
);
3379 /// Build a new C++ "this" expression.
3381 /// By default, performs semantic analysis to build a new "this" expression.
3382 /// Subclasses may override this routine to provide different behavior.
3383 ExprResult
RebuildCXXThisExpr(SourceLocation ThisLoc
,
3386 if (getSema().CheckCXXThisType(ThisLoc
, ThisType
))
3388 return getSema().BuildCXXThisExpr(ThisLoc
, ThisType
, isImplicit
);
3391 /// Build a new C++ throw expression.
3393 /// By default, performs semantic analysis to build the new expression.
3394 /// Subclasses may override this routine to provide different behavior.
3395 ExprResult
RebuildCXXThrowExpr(SourceLocation ThrowLoc
, Expr
*Sub
,
3396 bool IsThrownVariableInScope
) {
3397 return getSema().BuildCXXThrow(ThrowLoc
, Sub
, IsThrownVariableInScope
);
3400 /// Build a new C++ default-argument expression.
3402 /// By default, builds a new default-argument expression, which does not
3403 /// require any semantic analysis. Subclasses may override this routine to
3404 /// provide different behavior.
3405 ExprResult
RebuildCXXDefaultArgExpr(SourceLocation Loc
, ParmVarDecl
*Param
,
3406 Expr
*RewrittenExpr
) {
3407 return CXXDefaultArgExpr::Create(getSema().Context
, Loc
, Param
,
3408 RewrittenExpr
, getSema().CurContext
);
3411 /// Build a new C++11 default-initialization expression.
3413 /// By default, builds a new default field initialization expression, which
3414 /// does not require any semantic analysis. Subclasses may override this
3415 /// routine to provide different behavior.
3416 ExprResult
RebuildCXXDefaultInitExpr(SourceLocation Loc
,
3418 return getSema().BuildCXXDefaultInitExpr(Loc
, Field
);
3421 /// Build a new C++ zero-initialization expression.
3423 /// By default, performs semantic analysis to build the new expression.
3424 /// Subclasses may override this routine to provide different behavior.
3425 ExprResult
RebuildCXXScalarValueInitExpr(TypeSourceInfo
*TSInfo
,
3426 SourceLocation LParenLoc
,
3427 SourceLocation RParenLoc
) {
3428 return getSema().BuildCXXTypeConstructExpr(TSInfo
, LParenLoc
, {}, RParenLoc
,
3429 /*ListInitialization=*/false);
3432 /// Build a new C++ "new" expression.
3434 /// By default, performs semantic analysis to build the new expression.
3435 /// Subclasses may override this routine to provide different behavior.
3436 ExprResult
RebuildCXXNewExpr(SourceLocation StartLoc
, bool UseGlobal
,
3437 SourceLocation PlacementLParen
,
3438 MultiExprArg PlacementArgs
,
3439 SourceLocation PlacementRParen
,
3440 SourceRange TypeIdParens
, QualType AllocatedType
,
3441 TypeSourceInfo
*AllocatedTypeInfo
,
3442 std::optional
<Expr
*> ArraySize
,
3443 SourceRange DirectInitRange
, Expr
*Initializer
) {
3444 return getSema().BuildCXXNew(StartLoc
, UseGlobal
,
3456 /// Build a new C++ "delete" expression.
3458 /// By default, performs semantic analysis to build the new expression.
3459 /// Subclasses may override this routine to provide different behavior.
3460 ExprResult
RebuildCXXDeleteExpr(SourceLocation StartLoc
,
3461 bool IsGlobalDelete
,
3464 return getSema().ActOnCXXDelete(StartLoc
, IsGlobalDelete
, IsArrayForm
,
3468 /// Build a new type trait expression.
3470 /// By default, performs semantic analysis to build the new expression.
3471 /// Subclasses may override this routine to provide different behavior.
3472 ExprResult
RebuildTypeTrait(TypeTrait Trait
,
3473 SourceLocation StartLoc
,
3474 ArrayRef
<TypeSourceInfo
*> Args
,
3475 SourceLocation RParenLoc
) {
3476 return getSema().BuildTypeTrait(Trait
, StartLoc
, Args
, RParenLoc
);
3479 /// Build a new array type trait expression.
3481 /// By default, performs semantic analysis to build the new expression.
3482 /// Subclasses may override this routine to provide different behavior.
3483 ExprResult
RebuildArrayTypeTrait(ArrayTypeTrait Trait
,
3484 SourceLocation StartLoc
,
3485 TypeSourceInfo
*TSInfo
,
3487 SourceLocation RParenLoc
) {
3488 return getSema().BuildArrayTypeTrait(Trait
, StartLoc
, TSInfo
, DimExpr
, RParenLoc
);
3491 /// Build a new expression trait expression.
3493 /// By default, performs semantic analysis to build the new expression.
3494 /// Subclasses may override this routine to provide different behavior.
3495 ExprResult
RebuildExpressionTrait(ExpressionTrait Trait
,
3496 SourceLocation StartLoc
,
3498 SourceLocation RParenLoc
) {
3499 return getSema().BuildExpressionTrait(Trait
, StartLoc
, Queried
, RParenLoc
);
3502 /// Build a new (previously unresolved) declaration reference
3505 /// By default, performs semantic analysis to build the new expression.
3506 /// Subclasses may override this routine to provide different behavior.
3507 ExprResult
RebuildDependentScopeDeclRefExpr(
3508 NestedNameSpecifierLoc QualifierLoc
,
3509 SourceLocation TemplateKWLoc
,
3510 const DeclarationNameInfo
&NameInfo
,
3511 const TemplateArgumentListInfo
*TemplateArgs
,
3512 bool IsAddressOfOperand
,
3513 TypeSourceInfo
**RecoveryTSI
) {
3515 SS
.Adopt(QualifierLoc
);
3517 if (TemplateArgs
|| TemplateKWLoc
.isValid())
3518 return getSema().BuildQualifiedTemplateIdExpr(
3519 SS
, TemplateKWLoc
, NameInfo
, TemplateArgs
, IsAddressOfOperand
);
3521 return getSema().BuildQualifiedDeclarationNameExpr(
3522 SS
, NameInfo
, IsAddressOfOperand
, RecoveryTSI
);
3525 /// Build a new template-id expression.
3527 /// By default, performs semantic analysis to build the new expression.
3528 /// Subclasses may override this routine to provide different behavior.
3529 ExprResult
RebuildTemplateIdExpr(const CXXScopeSpec
&SS
,
3530 SourceLocation TemplateKWLoc
,
3533 const TemplateArgumentListInfo
*TemplateArgs
) {
3534 return getSema().BuildTemplateIdExpr(SS
, TemplateKWLoc
, R
, RequiresADL
,
3538 /// Build a new object-construction expression.
3540 /// By default, performs semantic analysis to build the new expression.
3541 /// Subclasses may override this routine to provide different behavior.
3542 ExprResult
RebuildCXXConstructExpr(
3543 QualType T
, SourceLocation Loc
, CXXConstructorDecl
*Constructor
,
3544 bool IsElidable
, MultiExprArg Args
, bool HadMultipleCandidates
,
3545 bool ListInitialization
, bool StdInitListInitialization
,
3546 bool RequiresZeroInit
, CXXConstructionKind ConstructKind
,
3547 SourceRange ParenRange
) {
3548 // Reconstruct the constructor we originally found, which might be
3549 // different if this is a call to an inherited constructor.
3550 CXXConstructorDecl
*FoundCtor
= Constructor
;
3551 if (Constructor
->isInheritingConstructor())
3552 FoundCtor
= Constructor
->getInheritedConstructor().getConstructor();
3554 SmallVector
<Expr
*, 8> ConvertedArgs
;
3555 if (getSema().CompleteConstructorCall(FoundCtor
, T
, Args
, Loc
,
3559 return getSema().BuildCXXConstructExpr(Loc
, T
, Constructor
,
3562 HadMultipleCandidates
,
3564 StdInitListInitialization
,
3565 RequiresZeroInit
, ConstructKind
,
3569 /// Build a new implicit construction via inherited constructor
3571 ExprResult
RebuildCXXInheritedCtorInitExpr(QualType T
, SourceLocation Loc
,
3572 CXXConstructorDecl
*Constructor
,
3573 bool ConstructsVBase
,
3574 bool InheritedFromVBase
) {
3575 return new (getSema().Context
) CXXInheritedCtorInitExpr(
3576 Loc
, T
, Constructor
, ConstructsVBase
, InheritedFromVBase
);
3579 /// Build a new object-construction expression.
3581 /// By default, performs semantic analysis to build the new expression.
3582 /// Subclasses may override this routine to provide different behavior.
3583 ExprResult
RebuildCXXTemporaryObjectExpr(TypeSourceInfo
*TSInfo
,
3584 SourceLocation LParenOrBraceLoc
,
3586 SourceLocation RParenOrBraceLoc
,
3587 bool ListInitialization
) {
3588 return getSema().BuildCXXTypeConstructExpr(
3589 TSInfo
, LParenOrBraceLoc
, Args
, RParenOrBraceLoc
, ListInitialization
);
3592 /// Build a new object-construction expression.
3594 /// By default, performs semantic analysis to build the new expression.
3595 /// Subclasses may override this routine to provide different behavior.
3596 ExprResult
RebuildCXXUnresolvedConstructExpr(TypeSourceInfo
*TSInfo
,
3597 SourceLocation LParenLoc
,
3599 SourceLocation RParenLoc
,
3600 bool ListInitialization
) {
3601 return getSema().BuildCXXTypeConstructExpr(TSInfo
, LParenLoc
, Args
,
3602 RParenLoc
, ListInitialization
);
3605 /// Build a new member reference expression.
3607 /// By default, performs semantic analysis to build the new expression.
3608 /// Subclasses may override this routine to provide different behavior.
3609 ExprResult
RebuildCXXDependentScopeMemberExpr(Expr
*BaseE
,
3612 SourceLocation OperatorLoc
,
3613 NestedNameSpecifierLoc QualifierLoc
,
3614 SourceLocation TemplateKWLoc
,
3615 NamedDecl
*FirstQualifierInScope
,
3616 const DeclarationNameInfo
&MemberNameInfo
,
3617 const TemplateArgumentListInfo
*TemplateArgs
) {
3619 SS
.Adopt(QualifierLoc
);
3621 return SemaRef
.BuildMemberReferenceExpr(BaseE
, BaseType
,
3622 OperatorLoc
, IsArrow
,
3624 FirstQualifierInScope
,
3626 TemplateArgs
, /*S*/nullptr);
3629 /// Build a new member reference expression.
3631 /// By default, performs semantic analysis to build the new expression.
3632 /// Subclasses may override this routine to provide different behavior.
3633 ExprResult
RebuildUnresolvedMemberExpr(Expr
*BaseE
, QualType BaseType
,
3634 SourceLocation OperatorLoc
,
3636 NestedNameSpecifierLoc QualifierLoc
,
3637 SourceLocation TemplateKWLoc
,
3638 NamedDecl
*FirstQualifierInScope
,
3640 const TemplateArgumentListInfo
*TemplateArgs
) {
3642 SS
.Adopt(QualifierLoc
);
3644 return SemaRef
.BuildMemberReferenceExpr(BaseE
, BaseType
,
3645 OperatorLoc
, IsArrow
,
3647 FirstQualifierInScope
,
3648 R
, TemplateArgs
, /*S*/nullptr);
3651 /// Build a new noexcept expression.
3653 /// By default, performs semantic analysis to build the new expression.
3654 /// Subclasses may override this routine to provide different behavior.
3655 ExprResult
RebuildCXXNoexceptExpr(SourceRange Range
, Expr
*Arg
) {
3656 return SemaRef
.BuildCXXNoexceptExpr(Range
.getBegin(), Arg
, Range
.getEnd());
3659 /// Build a new expression to compute the length of a parameter pack.
3660 ExprResult
RebuildSizeOfPackExpr(SourceLocation OperatorLoc
, NamedDecl
*Pack
,
3661 SourceLocation PackLoc
,
3662 SourceLocation RParenLoc
,
3663 std::optional
<unsigned> Length
,
3664 ArrayRef
<TemplateArgument
> PartialArgs
) {
3665 return SizeOfPackExpr::Create(SemaRef
.Context
, OperatorLoc
, Pack
, PackLoc
,
3666 RParenLoc
, Length
, PartialArgs
);
3669 ExprResult
RebuildPackIndexingExpr(SourceLocation EllipsisLoc
,
3670 SourceLocation RSquareLoc
,
3671 Expr
*PackIdExpression
, Expr
*IndexExpr
,
3672 ArrayRef
<Expr
*> ExpandedExprs
,
3673 bool FullySubstituted
= false) {
3674 return getSema().BuildPackIndexingExpr(PackIdExpression
, EllipsisLoc
,
3675 IndexExpr
, RSquareLoc
, ExpandedExprs
,
3679 /// Build a new expression representing a call to a source location
3682 /// By default, performs semantic analysis to build the new expression.
3683 /// Subclasses may override this routine to provide different behavior.
3684 ExprResult
RebuildSourceLocExpr(SourceLocIdentKind Kind
, QualType ResultTy
,
3685 SourceLocation BuiltinLoc
,
3686 SourceLocation RPLoc
,
3687 DeclContext
*ParentContext
) {
3688 return getSema().BuildSourceLocExpr(Kind
, ResultTy
, BuiltinLoc
, RPLoc
,
3692 /// Build a new Objective-C boxed expression.
3694 /// By default, performs semantic analysis to build the new expression.
3695 /// Subclasses may override this routine to provide different behavior.
3696 ExprResult
RebuildConceptSpecializationExpr(NestedNameSpecifierLoc NNS
,
3697 SourceLocation TemplateKWLoc
, DeclarationNameInfo ConceptNameInfo
,
3698 NamedDecl
*FoundDecl
, ConceptDecl
*NamedConcept
,
3699 TemplateArgumentListInfo
*TALI
) {
3702 ExprResult Result
= getSema().CheckConceptTemplateId(SS
, TemplateKWLoc
,
3705 NamedConcept
, TALI
);
3706 if (Result
.isInvalid())
3711 /// \brief Build a new requires expression.
3713 /// By default, performs semantic analysis to build the new expression.
3714 /// Subclasses may override this routine to provide different behavior.
3715 ExprResult
RebuildRequiresExpr(SourceLocation RequiresKWLoc
,
3716 RequiresExprBodyDecl
*Body
,
3717 SourceLocation LParenLoc
,
3718 ArrayRef
<ParmVarDecl
*> LocalParameters
,
3719 SourceLocation RParenLoc
,
3720 ArrayRef
<concepts::Requirement
*> Requirements
,
3721 SourceLocation ClosingBraceLoc
) {
3722 return RequiresExpr::Create(SemaRef
.Context
, RequiresKWLoc
, Body
, LParenLoc
,
3723 LocalParameters
, RParenLoc
, Requirements
,
3727 concepts::TypeRequirement
*
3728 RebuildTypeRequirement(
3729 concepts::Requirement::SubstitutionDiagnostic
*SubstDiag
) {
3730 return SemaRef
.BuildTypeRequirement(SubstDiag
);
3733 concepts::TypeRequirement
*RebuildTypeRequirement(TypeSourceInfo
*T
) {
3734 return SemaRef
.BuildTypeRequirement(T
);
3737 concepts::ExprRequirement
*
3738 RebuildExprRequirement(
3739 concepts::Requirement::SubstitutionDiagnostic
*SubstDiag
, bool IsSimple
,
3740 SourceLocation NoexceptLoc
,
3741 concepts::ExprRequirement::ReturnTypeRequirement Ret
) {
3742 return SemaRef
.BuildExprRequirement(SubstDiag
, IsSimple
, NoexceptLoc
,
3746 concepts::ExprRequirement
*
3747 RebuildExprRequirement(Expr
*E
, bool IsSimple
, SourceLocation NoexceptLoc
,
3748 concepts::ExprRequirement::ReturnTypeRequirement Ret
) {
3749 return SemaRef
.BuildExprRequirement(E
, IsSimple
, NoexceptLoc
,
3753 concepts::NestedRequirement
*
3754 RebuildNestedRequirement(StringRef InvalidConstraintEntity
,
3755 const ASTConstraintSatisfaction
&Satisfaction
) {
3756 return SemaRef
.BuildNestedRequirement(InvalidConstraintEntity
,
3760 concepts::NestedRequirement
*RebuildNestedRequirement(Expr
*Constraint
) {
3761 return SemaRef
.BuildNestedRequirement(Constraint
);
3764 /// \brief Build a new Objective-C boxed expression.
3766 /// By default, performs semantic analysis to build the new expression.
3767 /// Subclasses may override this routine to provide different behavior.
3768 ExprResult
RebuildObjCBoxedExpr(SourceRange SR
, Expr
*ValueExpr
) {
3769 return getSema().ObjC().BuildObjCBoxedExpr(SR
, ValueExpr
);
3772 /// Build a new Objective-C array literal.
3774 /// By default, performs semantic analysis to build the new expression.
3775 /// Subclasses may override this routine to provide different behavior.
3776 ExprResult
RebuildObjCArrayLiteral(SourceRange Range
,
3777 Expr
**Elements
, unsigned NumElements
) {
3778 return getSema().ObjC().BuildObjCArrayLiteral(
3779 Range
, MultiExprArg(Elements
, NumElements
));
3782 ExprResult
RebuildObjCSubscriptRefExpr(SourceLocation RB
,
3783 Expr
*Base
, Expr
*Key
,
3784 ObjCMethodDecl
*getterMethod
,
3785 ObjCMethodDecl
*setterMethod
) {
3786 return getSema().ObjC().BuildObjCSubscriptExpression(
3787 RB
, Base
, Key
, getterMethod
, setterMethod
);
3790 /// Build a new Objective-C dictionary literal.
3792 /// By default, performs semantic analysis to build the new expression.
3793 /// Subclasses may override this routine to provide different behavior.
3794 ExprResult
RebuildObjCDictionaryLiteral(SourceRange Range
,
3795 MutableArrayRef
<ObjCDictionaryElement
> Elements
) {
3796 return getSema().ObjC().BuildObjCDictionaryLiteral(Range
, Elements
);
3799 /// Build a new Objective-C \@encode expression.
3801 /// By default, performs semantic analysis to build the new expression.
3802 /// Subclasses may override this routine to provide different behavior.
3803 ExprResult
RebuildObjCEncodeExpr(SourceLocation AtLoc
,
3804 TypeSourceInfo
*EncodeTypeInfo
,
3805 SourceLocation RParenLoc
) {
3806 return SemaRef
.ObjC().BuildObjCEncodeExpression(AtLoc
, EncodeTypeInfo
,
3810 /// Build a new Objective-C class message.
3811 ExprResult
RebuildObjCMessageExpr(TypeSourceInfo
*ReceiverTypeInfo
,
3813 ArrayRef
<SourceLocation
> SelectorLocs
,
3814 ObjCMethodDecl
*Method
,
3815 SourceLocation LBracLoc
,
3817 SourceLocation RBracLoc
) {
3818 return SemaRef
.ObjC().BuildClassMessage(
3819 ReceiverTypeInfo
, ReceiverTypeInfo
->getType(),
3820 /*SuperLoc=*/SourceLocation(), Sel
, Method
, LBracLoc
, SelectorLocs
,
3824 /// Build a new Objective-C instance message.
3825 ExprResult
RebuildObjCMessageExpr(Expr
*Receiver
,
3827 ArrayRef
<SourceLocation
> SelectorLocs
,
3828 ObjCMethodDecl
*Method
,
3829 SourceLocation LBracLoc
,
3831 SourceLocation RBracLoc
) {
3832 return SemaRef
.ObjC().BuildInstanceMessage(Receiver
, Receiver
->getType(),
3833 /*SuperLoc=*/SourceLocation(),
3834 Sel
, Method
, LBracLoc
,
3835 SelectorLocs
, RBracLoc
, Args
);
3838 /// Build a new Objective-C instance/class message to 'super'.
3839 ExprResult
RebuildObjCMessageExpr(SourceLocation SuperLoc
,
3841 ArrayRef
<SourceLocation
> SelectorLocs
,
3843 ObjCMethodDecl
*Method
,
3844 SourceLocation LBracLoc
,
3846 SourceLocation RBracLoc
) {
3847 return Method
->isInstanceMethod()
3848 ? SemaRef
.ObjC().BuildInstanceMessage(
3849 nullptr, SuperType
, SuperLoc
, Sel
, Method
, LBracLoc
,
3850 SelectorLocs
, RBracLoc
, Args
)
3851 : SemaRef
.ObjC().BuildClassMessage(nullptr, SuperType
, SuperLoc
,
3852 Sel
, Method
, LBracLoc
,
3853 SelectorLocs
, RBracLoc
, Args
);
3856 /// Build a new Objective-C ivar reference expression.
3858 /// By default, performs semantic analysis to build the new expression.
3859 /// Subclasses may override this routine to provide different behavior.
3860 ExprResult
RebuildObjCIvarRefExpr(Expr
*BaseArg
, ObjCIvarDecl
*Ivar
,
3861 SourceLocation IvarLoc
,
3862 bool IsArrow
, bool IsFreeIvar
) {
3864 DeclarationNameInfo
NameInfo(Ivar
->getDeclName(), IvarLoc
);
3865 ExprResult Result
= getSema().BuildMemberReferenceExpr(
3866 BaseArg
, BaseArg
->getType(),
3867 /*FIXME:*/ IvarLoc
, IsArrow
, SS
, SourceLocation(),
3868 /*FirstQualifierInScope=*/nullptr, NameInfo
,
3869 /*TemplateArgs=*/nullptr,
3871 if (IsFreeIvar
&& Result
.isUsable())
3872 cast
<ObjCIvarRefExpr
>(Result
.get())->setIsFreeIvar(IsFreeIvar
);
3876 /// Build a new Objective-C property reference expression.
3878 /// By default, performs semantic analysis to build the new expression.
3879 /// Subclasses may override this routine to provide different behavior.
3880 ExprResult
RebuildObjCPropertyRefExpr(Expr
*BaseArg
,
3881 ObjCPropertyDecl
*Property
,
3882 SourceLocation PropertyLoc
) {
3884 DeclarationNameInfo
NameInfo(Property
->getDeclName(), PropertyLoc
);
3885 return getSema().BuildMemberReferenceExpr(BaseArg
, BaseArg
->getType(),
3886 /*FIXME:*/PropertyLoc
,
3888 SS
, SourceLocation(),
3889 /*FirstQualifierInScope=*/nullptr,
3891 /*TemplateArgs=*/nullptr,
3895 /// Build a new Objective-C property reference expression.
3897 /// By default, performs semantic analysis to build the new expression.
3898 /// Subclasses may override this routine to provide different behavior.
3899 ExprResult
RebuildObjCPropertyRefExpr(Expr
*Base
, QualType T
,
3900 ObjCMethodDecl
*Getter
,
3901 ObjCMethodDecl
*Setter
,
3902 SourceLocation PropertyLoc
) {
3903 // Since these expressions can only be value-dependent, we do not
3904 // need to perform semantic analysis again.
3906 new (getSema().Context
) ObjCPropertyRefExpr(Getter
, Setter
, T
,
3907 VK_LValue
, OK_ObjCProperty
,
3908 PropertyLoc
, Base
));
3911 /// Build a new Objective-C "isa" expression.
3913 /// By default, performs semantic analysis to build the new expression.
3914 /// Subclasses may override this routine to provide different behavior.
3915 ExprResult
RebuildObjCIsaExpr(Expr
*BaseArg
, SourceLocation IsaLoc
,
3916 SourceLocation OpLoc
, bool IsArrow
) {
3918 DeclarationNameInfo
NameInfo(&getSema().Context
.Idents
.get("isa"), IsaLoc
);
3919 return getSema().BuildMemberReferenceExpr(BaseArg
, BaseArg
->getType(),
3921 SS
, SourceLocation(),
3922 /*FirstQualifierInScope=*/nullptr,
3924 /*TemplateArgs=*/nullptr,
3928 /// Build a new shuffle vector expression.
3930 /// By default, performs semantic analysis to build the new expression.
3931 /// Subclasses may override this routine to provide different behavior.
3932 ExprResult
RebuildShuffleVectorExpr(SourceLocation BuiltinLoc
,
3933 MultiExprArg SubExprs
,
3934 SourceLocation RParenLoc
) {
3935 // Find the declaration for __builtin_shufflevector
3936 const IdentifierInfo
&Name
3937 = SemaRef
.Context
.Idents
.get("__builtin_shufflevector");
3938 TranslationUnitDecl
*TUDecl
= SemaRef
.Context
.getTranslationUnitDecl();
3939 DeclContext::lookup_result Lookup
= TUDecl
->lookup(DeclarationName(&Name
));
3940 assert(!Lookup
.empty() && "No __builtin_shufflevector?");
3942 // Build a reference to the __builtin_shufflevector builtin
3943 FunctionDecl
*Builtin
= cast
<FunctionDecl
>(Lookup
.front());
3944 Expr
*Callee
= new (SemaRef
.Context
)
3945 DeclRefExpr(SemaRef
.Context
, Builtin
, false,
3946 SemaRef
.Context
.BuiltinFnTy
, VK_PRValue
, BuiltinLoc
);
3947 QualType CalleePtrTy
= SemaRef
.Context
.getPointerType(Builtin
->getType());
3948 Callee
= SemaRef
.ImpCastExprToType(Callee
, CalleePtrTy
,
3949 CK_BuiltinFnToFnPtr
).get();
3951 // Build the CallExpr
3952 ExprResult TheCall
= CallExpr::Create(
3953 SemaRef
.Context
, Callee
, SubExprs
, Builtin
->getCallResultType(),
3954 Expr::getValueKindForType(Builtin
->getReturnType()), RParenLoc
,
3955 FPOptionsOverride());
3957 // Type-check the __builtin_shufflevector expression.
3958 return SemaRef
.BuiltinShuffleVector(cast
<CallExpr
>(TheCall
.get()));
3961 /// Build a new convert vector expression.
3962 ExprResult
RebuildConvertVectorExpr(SourceLocation BuiltinLoc
,
3963 Expr
*SrcExpr
, TypeSourceInfo
*DstTInfo
,
3964 SourceLocation RParenLoc
) {
3965 return SemaRef
.ConvertVectorExpr(SrcExpr
, DstTInfo
, BuiltinLoc
, RParenLoc
);
3968 /// Build a new template argument pack expansion.
3970 /// By default, performs semantic analysis to build a new pack expansion
3971 /// for a template argument. Subclasses may override this routine to provide
3972 /// different behavior.
3974 RebuildPackExpansion(TemplateArgumentLoc Pattern
, SourceLocation EllipsisLoc
,
3975 std::optional
<unsigned> NumExpansions
) {
3976 switch (Pattern
.getArgument().getKind()) {
3977 case TemplateArgument::Expression
: {
3979 = getSema().CheckPackExpansion(Pattern
.getSourceExpression(),
3980 EllipsisLoc
, NumExpansions
);
3981 if (Result
.isInvalid())
3982 return TemplateArgumentLoc();
3984 return TemplateArgumentLoc(Result
.get(), Result
.get());
3987 case TemplateArgument::Template
:
3988 return TemplateArgumentLoc(
3990 TemplateArgument(Pattern
.getArgument().getAsTemplate(),
3992 Pattern
.getTemplateQualifierLoc(), Pattern
.getTemplateNameLoc(),
3995 case TemplateArgument::Null
:
3996 case TemplateArgument::Integral
:
3997 case TemplateArgument::Declaration
:
3998 case TemplateArgument::StructuralValue
:
3999 case TemplateArgument::Pack
:
4000 case TemplateArgument::TemplateExpansion
:
4001 case TemplateArgument::NullPtr
:
4002 llvm_unreachable("Pack expansion pattern has no parameter packs");
4004 case TemplateArgument::Type
:
4005 if (TypeSourceInfo
*Expansion
4006 = getSema().CheckPackExpansion(Pattern
.getTypeSourceInfo(),
4009 return TemplateArgumentLoc(TemplateArgument(Expansion
->getType()),
4014 return TemplateArgumentLoc();
4017 /// Build a new expression pack expansion.
4019 /// By default, performs semantic analysis to build a new pack expansion
4020 /// for an expression. Subclasses may override this routine to provide
4021 /// different behavior.
4022 ExprResult
RebuildPackExpansion(Expr
*Pattern
, SourceLocation EllipsisLoc
,
4023 std::optional
<unsigned> NumExpansions
) {
4024 return getSema().CheckPackExpansion(Pattern
, EllipsisLoc
, NumExpansions
);
4027 /// Build a new C++1z fold-expression.
4029 /// By default, performs semantic analysis in order to build a new fold
4031 ExprResult
RebuildCXXFoldExpr(UnresolvedLookupExpr
*ULE
,
4032 SourceLocation LParenLoc
, Expr
*LHS
,
4033 BinaryOperatorKind Operator
,
4034 SourceLocation EllipsisLoc
, Expr
*RHS
,
4035 SourceLocation RParenLoc
,
4036 std::optional
<unsigned> NumExpansions
) {
4037 return getSema().BuildCXXFoldExpr(ULE
, LParenLoc
, LHS
, Operator
,
4038 EllipsisLoc
, RHS
, RParenLoc
,
4042 ExprResult
RebuildLambdaExpr(SourceLocation StartLoc
, SourceLocation EndLoc
,
4043 LambdaScopeInfo
*LSI
) {
4044 for (ParmVarDecl
*PVD
: LSI
->CallOperator
->parameters()) {
4045 if (Expr
*Init
= PVD
->getInit())
4046 LSI
->ContainsUnexpandedParameterPack
|=
4047 Init
->containsUnexpandedParameterPack();
4048 else if (PVD
->hasUninstantiatedDefaultArg())
4049 LSI
->ContainsUnexpandedParameterPack
|=
4050 PVD
->getUninstantiatedDefaultArg()
4051 ->containsUnexpandedParameterPack();
4053 return getSema().BuildLambdaExpr(StartLoc
, EndLoc
, LSI
);
4056 /// Build an empty C++1z fold-expression with the given operator.
4058 /// By default, produces the fallback value for the fold-expression, or
4059 /// produce an error if there is no fallback value.
4060 ExprResult
RebuildEmptyCXXFoldExpr(SourceLocation EllipsisLoc
,
4061 BinaryOperatorKind Operator
) {
4062 return getSema().BuildEmptyCXXFoldExpr(EllipsisLoc
, Operator
);
4065 /// Build a new atomic operation expression.
4067 /// By default, performs semantic analysis to build the new expression.
4068 /// Subclasses may override this routine to provide different behavior.
4069 ExprResult
RebuildAtomicExpr(SourceLocation BuiltinLoc
, MultiExprArg SubExprs
,
4070 AtomicExpr::AtomicOp Op
,
4071 SourceLocation RParenLoc
) {
4072 // Use this for all of the locations, since we don't know the difference
4073 // between the call and the expr at this point.
4074 SourceRange Range
{BuiltinLoc
, RParenLoc
};
4075 return getSema().BuildAtomicExpr(Range
, Range
, RParenLoc
, SubExprs
, Op
,
4076 Sema::AtomicArgumentOrder::AST
);
4079 ExprResult
RebuildRecoveryExpr(SourceLocation BeginLoc
, SourceLocation EndLoc
,
4080 ArrayRef
<Expr
*> SubExprs
, QualType Type
) {
4081 return getSema().CreateRecoveryExpr(BeginLoc
, EndLoc
, SubExprs
, Type
);
4084 StmtResult
RebuildOpenACCComputeConstruct(OpenACCDirectiveKind K
,
4085 SourceLocation BeginLoc
,
4086 SourceLocation DirLoc
,
4087 SourceLocation EndLoc
,
4088 ArrayRef
<OpenACCClause
*> Clauses
,
4089 StmtResult StrBlock
) {
4090 return getSema().OpenACC().ActOnEndStmtDirective(K
, BeginLoc
, DirLoc
,
4091 EndLoc
, Clauses
, StrBlock
);
4094 StmtResult
RebuildOpenACCLoopConstruct(SourceLocation BeginLoc
,
4095 SourceLocation DirLoc
,
4096 SourceLocation EndLoc
,
4097 ArrayRef
<OpenACCClause
*> Clauses
,
4099 return getSema().OpenACC().ActOnEndStmtDirective(
4100 OpenACCDirectiveKind::Loop
, BeginLoc
, DirLoc
, EndLoc
, Clauses
, Loop
);
4103 StmtResult
RebuildOpenACCCombinedConstruct(OpenACCDirectiveKind K
,
4104 SourceLocation BeginLoc
,
4105 SourceLocation DirLoc
,
4106 SourceLocation EndLoc
,
4107 ArrayRef
<OpenACCClause
*> Clauses
,
4109 return getSema().OpenACC().ActOnEndStmtDirective(K
, BeginLoc
, DirLoc
,
4110 EndLoc
, Clauses
, Loop
);
4113 ExprResult
RebuildOpenACCAsteriskSizeExpr(SourceLocation AsteriskLoc
) {
4114 return getSema().OpenACC().ActOnOpenACCAsteriskSizeExpr(AsteriskLoc
);
4118 TypeLoc
TransformTypeInObjectScope(TypeLoc TL
,
4119 QualType ObjectType
,
4120 NamedDecl
*FirstQualifierInScope
,
4123 TypeSourceInfo
*TransformTypeInObjectScope(TypeSourceInfo
*TSInfo
,
4124 QualType ObjectType
,
4125 NamedDecl
*FirstQualifierInScope
,
4128 TypeSourceInfo
*TransformTSIInObjectScope(TypeLoc TL
, QualType ObjectType
,
4129 NamedDecl
*FirstQualifierInScope
,
4132 QualType
TransformDependentNameType(TypeLocBuilder
&TLB
,
4133 DependentNameTypeLoc TL
,
4134 bool DeducibleTSTContext
);
4136 llvm::SmallVector
<OpenACCClause
*>
4137 TransformOpenACCClauseList(OpenACCDirectiveKind DirKind
,
4138 ArrayRef
<const OpenACCClause
*> OldClauses
);
4141 TransformOpenACCClause(ArrayRef
<const OpenACCClause
*> ExistingClauses
,
4142 OpenACCDirectiveKind DirKind
,
4143 const OpenACCClause
*OldClause
);
4146 template <typename Derived
>
4147 StmtResult TreeTransform
<Derived
>::TransformStmt(Stmt
*S
, StmtDiscardKind SDK
) {
4151 switch (S
->getStmtClass()) {
4152 case Stmt::NoStmtClass
: break;
4154 // Transform individual statement nodes
4155 // Pass SDK into statements that can produce a value
4156 #define STMT(Node, Parent) \
4157 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(S));
4158 #define VALUESTMT(Node, Parent) \
4159 case Stmt::Node##Class: \
4160 return getDerived().Transform##Node(cast<Node>(S), SDK);
4161 #define ABSTRACT_STMT(Node)
4162 #define EXPR(Node, Parent)
4163 #include "clang/AST/StmtNodes.inc"
4165 // Transform expressions by calling TransformExpr.
4166 #define STMT(Node, Parent)
4167 #define ABSTRACT_STMT(Stmt)
4168 #define EXPR(Node, Parent) case Stmt::Node##Class:
4169 #include "clang/AST/StmtNodes.inc"
4171 ExprResult E
= getDerived().TransformExpr(cast
<Expr
>(S
));
4173 if (SDK
== SDK_StmtExprResult
)
4174 E
= getSema().ActOnStmtExprResult(E
);
4175 return getSema().ActOnExprStmt(E
, SDK
== SDK_Discarded
);
4182 template<typename Derived
>
4183 OMPClause
*TreeTransform
<Derived
>::TransformOMPClause(OMPClause
*S
) {
4187 switch (S
->getClauseKind()) {
4189 // Transform individual clause nodes
4190 #define GEN_CLANG_CLAUSE_CLASS
4191 #define CLAUSE_CLASS(Enum, Str, Class) \
4193 return getDerived().Transform##Class(cast<Class>(S));
4194 #include "llvm/Frontend/OpenMP/OMP.inc"
4201 template<typename Derived
>
4202 ExprResult TreeTransform
<Derived
>::TransformExpr(Expr
*E
) {
4206 switch (E
->getStmtClass()) {
4207 case Stmt::NoStmtClass
: break;
4208 #define STMT(Node, Parent) case Stmt::Node##Class: break;
4209 #define ABSTRACT_STMT(Stmt)
4210 #define EXPR(Node, Parent) \
4211 case Stmt::Node##Class: return getDerived().Transform##Node(cast<Node>(E));
4212 #include "clang/AST/StmtNodes.inc"
4218 template<typename Derived
>
4219 ExprResult TreeTransform
<Derived
>::TransformInitializer(Expr
*Init
,
4221 // Initializers are instantiated like expressions, except that various outer
4222 // layers are stripped.
4226 if (auto *FE
= dyn_cast
<FullExpr
>(Init
))
4227 Init
= FE
->getSubExpr();
4229 if (auto *AIL
= dyn_cast
<ArrayInitLoopExpr
>(Init
)) {
4230 OpaqueValueExpr
*OVE
= AIL
->getCommonExpr();
4231 Init
= OVE
->getSourceExpr();
4234 if (MaterializeTemporaryExpr
*MTE
= dyn_cast
<MaterializeTemporaryExpr
>(Init
))
4235 Init
= MTE
->getSubExpr();
4237 while (CXXBindTemporaryExpr
*Binder
= dyn_cast
<CXXBindTemporaryExpr
>(Init
))
4238 Init
= Binder
->getSubExpr();
4240 if (ImplicitCastExpr
*ICE
= dyn_cast
<ImplicitCastExpr
>(Init
))
4241 Init
= ICE
->getSubExprAsWritten();
4243 if (CXXStdInitializerListExpr
*ILE
=
4244 dyn_cast
<CXXStdInitializerListExpr
>(Init
))
4245 return TransformInitializer(ILE
->getSubExpr(), NotCopyInit
);
4247 // If this is copy-initialization, we only need to reconstruct
4248 // InitListExprs. Other forms of copy-initialization will be a no-op if
4249 // the initializer is already the right type.
4250 CXXConstructExpr
*Construct
= dyn_cast
<CXXConstructExpr
>(Init
);
4251 if (!NotCopyInit
&& !(Construct
&& Construct
->isListInitialization()))
4252 return getDerived().TransformExpr(Init
);
4254 // Revert value-initialization back to empty parens.
4255 if (CXXScalarValueInitExpr
*VIE
= dyn_cast
<CXXScalarValueInitExpr
>(Init
)) {
4256 SourceRange Parens
= VIE
->getSourceRange();
4257 return getDerived().RebuildParenListExpr(Parens
.getBegin(), {},
4261 // FIXME: We shouldn't build ImplicitValueInitExprs for direct-initialization.
4262 if (isa
<ImplicitValueInitExpr
>(Init
))
4263 return getDerived().RebuildParenListExpr(SourceLocation(), {},
4266 // Revert initialization by constructor back to a parenthesized or braced list
4267 // of expressions. Any other form of initializer can just be reused directly.
4268 if (!Construct
|| isa
<CXXTemporaryObjectExpr
>(Construct
))
4269 return getDerived().TransformExpr(Init
);
4271 // If the initialization implicitly converted an initializer list to a
4272 // std::initializer_list object, unwrap the std::initializer_list too.
4273 if (Construct
&& Construct
->isStdInitListInitialization())
4274 return TransformInitializer(Construct
->getArg(0), NotCopyInit
);
4276 // Enter a list-init context if this was list initialization.
4277 EnterExpressionEvaluationContext
Context(
4278 getSema(), EnterExpressionEvaluationContext::InitList
,
4279 Construct
->isListInitialization());
4281 getSema().currentEvaluationContext().InLifetimeExtendingContext
=
4282 getSema().parentEvaluationContext().InLifetimeExtendingContext
;
4283 getSema().currentEvaluationContext().RebuildDefaultArgOrDefaultInit
=
4284 getSema().parentEvaluationContext().RebuildDefaultArgOrDefaultInit
;
4285 SmallVector
<Expr
*, 8> NewArgs
;
4286 bool ArgChanged
= false;
4287 if (getDerived().TransformExprs(Construct
->getArgs(), Construct
->getNumArgs(),
4288 /*IsCall*/true, NewArgs
, &ArgChanged
))
4291 // If this was list initialization, revert to syntactic list form.
4292 if (Construct
->isListInitialization())
4293 return getDerived().RebuildInitList(Construct
->getBeginLoc(), NewArgs
,
4294 Construct
->getEndLoc());
4296 // Build a ParenListExpr to represent anything else.
4297 SourceRange Parens
= Construct
->getParenOrBraceRange();
4298 if (Parens
.isInvalid()) {
4299 // This was a variable declaration's initialization for which no initializer
4301 assert(NewArgs
.empty() &&
4302 "no parens or braces but have direct init with arguments?");
4305 return getDerived().RebuildParenListExpr(Parens
.getBegin(), NewArgs
,
4309 template<typename Derived
>
4310 bool TreeTransform
<Derived
>::TransformExprs(Expr
*const *Inputs
,
4313 SmallVectorImpl
<Expr
*> &Outputs
,
4315 for (unsigned I
= 0; I
!= NumInputs
; ++I
) {
4316 // If requested, drop call arguments that need to be dropped.
4317 if (IsCall
&& getDerived().DropCallArgument(Inputs
[I
])) {
4324 if (PackExpansionExpr
*Expansion
= dyn_cast
<PackExpansionExpr
>(Inputs
[I
])) {
4325 Expr
*Pattern
= Expansion
->getPattern();
4327 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
4328 getSema().collectUnexpandedParameterPacks(Pattern
, Unexpanded
);
4329 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
4331 // Determine whether the set of unexpanded parameter packs can and should
4334 bool RetainExpansion
= false;
4335 std::optional
<unsigned> OrigNumExpansions
= Expansion
->getNumExpansions();
4336 std::optional
<unsigned> NumExpansions
= OrigNumExpansions
;
4337 if (getDerived().TryExpandParameterPacks(Expansion
->getEllipsisLoc(),
4338 Pattern
->getSourceRange(),
4340 Expand
, RetainExpansion
,
4345 // The transform has determined that we should perform a simple
4346 // transformation on the pack expansion, producing another pack
4348 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
4349 ExprResult OutPattern
= getDerived().TransformExpr(Pattern
);
4350 if (OutPattern
.isInvalid())
4353 ExprResult Out
= getDerived().RebuildPackExpansion(OutPattern
.get(),
4354 Expansion
->getEllipsisLoc(),
4356 if (Out
.isInvalid())
4361 Outputs
.push_back(Out
.get());
4365 // Record right away that the argument was changed. This needs
4366 // to happen even if the array expands to nothing.
4367 if (ArgChanged
) *ArgChanged
= true;
4369 // The transform has determined that we should perform an elementwise
4370 // expansion of the pattern. Do so.
4371 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
4372 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
4373 ExprResult Out
= getDerived().TransformExpr(Pattern
);
4374 if (Out
.isInvalid())
4377 if (Out
.get()->containsUnexpandedParameterPack()) {
4378 Out
= getDerived().RebuildPackExpansion(
4379 Out
.get(), Expansion
->getEllipsisLoc(), OrigNumExpansions
);
4380 if (Out
.isInvalid())
4384 Outputs
.push_back(Out
.get());
4387 // If we're supposed to retain a pack expansion, do so by temporarily
4388 // forgetting the partially-substituted parameter pack.
4389 if (RetainExpansion
) {
4390 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
4392 ExprResult Out
= getDerived().TransformExpr(Pattern
);
4393 if (Out
.isInvalid())
4396 Out
= getDerived().RebuildPackExpansion(
4397 Out
.get(), Expansion
->getEllipsisLoc(), OrigNumExpansions
);
4398 if (Out
.isInvalid())
4401 Outputs
.push_back(Out
.get());
4408 IsCall
? getDerived().TransformInitializer(Inputs
[I
], /*DirectInit*/false)
4409 : getDerived().TransformExpr(Inputs
[I
]);
4410 if (Result
.isInvalid())
4413 if (Result
.get() != Inputs
[I
] && ArgChanged
)
4416 Outputs
.push_back(Result
.get());
4422 template <typename Derived
>
4423 Sema::ConditionResult TreeTransform
<Derived
>::TransformCondition(
4424 SourceLocation Loc
, VarDecl
*Var
, Expr
*Expr
, Sema::ConditionKind Kind
) {
4426 VarDecl
*ConditionVar
= cast_or_null
<VarDecl
>(
4427 getDerived().TransformDefinition(Var
->getLocation(), Var
));
4430 return Sema::ConditionError();
4432 return getSema().ActOnConditionVariable(ConditionVar
, Loc
, Kind
);
4436 ExprResult CondExpr
= getDerived().TransformExpr(Expr
);
4438 if (CondExpr
.isInvalid())
4439 return Sema::ConditionError();
4441 return getSema().ActOnCondition(nullptr, Loc
, CondExpr
.get(), Kind
,
4442 /*MissingOK=*/true);
4445 return Sema::ConditionResult();
4448 template <typename Derived
>
4449 NestedNameSpecifierLoc TreeTransform
<Derived
>::TransformNestedNameSpecifierLoc(
4450 NestedNameSpecifierLoc NNS
, QualType ObjectType
,
4451 NamedDecl
*FirstQualifierInScope
) {
4452 SmallVector
<NestedNameSpecifierLoc
, 4> Qualifiers
;
4454 auto insertNNS
= [&Qualifiers
](NestedNameSpecifierLoc NNS
) {
4455 for (NestedNameSpecifierLoc Qualifier
= NNS
; Qualifier
;
4456 Qualifier
= Qualifier
.getPrefix())
4457 Qualifiers
.push_back(Qualifier
);
4462 while (!Qualifiers
.empty()) {
4463 NestedNameSpecifierLoc Q
= Qualifiers
.pop_back_val();
4464 NestedNameSpecifier
*QNNS
= Q
.getNestedNameSpecifier();
4466 switch (QNNS
->getKind()) {
4467 case NestedNameSpecifier::Identifier
: {
4468 Sema::NestedNameSpecInfo
IdInfo(QNNS
->getAsIdentifier(),
4469 Q
.getLocalBeginLoc(), Q
.getLocalEndLoc(),
4471 if (SemaRef
.BuildCXXNestedNameSpecifier(/*Scope=*/nullptr, IdInfo
, false,
4472 SS
, FirstQualifierInScope
, false))
4473 return NestedNameSpecifierLoc();
4477 case NestedNameSpecifier::Namespace
: {
4479 cast_or_null
<NamespaceDecl
>(getDerived().TransformDecl(
4480 Q
.getLocalBeginLoc(), QNNS
->getAsNamespace()));
4481 SS
.Extend(SemaRef
.Context
, NS
, Q
.getLocalBeginLoc(), Q
.getLocalEndLoc());
4485 case NestedNameSpecifier::NamespaceAlias
: {
4486 NamespaceAliasDecl
*Alias
=
4487 cast_or_null
<NamespaceAliasDecl
>(getDerived().TransformDecl(
4488 Q
.getLocalBeginLoc(), QNNS
->getAsNamespaceAlias()));
4489 SS
.Extend(SemaRef
.Context
, Alias
, Q
.getLocalBeginLoc(),
4490 Q
.getLocalEndLoc());
4494 case NestedNameSpecifier::Global
:
4495 // There is no meaningful transformation that one could perform on the
4497 SS
.MakeGlobal(SemaRef
.Context
, Q
.getBeginLoc());
4500 case NestedNameSpecifier::Super
: {
4502 cast_or_null
<CXXRecordDecl
>(getDerived().TransformDecl(
4503 SourceLocation(), QNNS
->getAsRecordDecl()));
4504 SS
.MakeSuper(SemaRef
.Context
, RD
, Q
.getBeginLoc(), Q
.getEndLoc());
4508 case NestedNameSpecifier::TypeSpecWithTemplate
:
4509 case NestedNameSpecifier::TypeSpec
: {
4510 TypeLoc TL
= TransformTypeInObjectScope(Q
.getTypeLoc(), ObjectType
,
4511 FirstQualifierInScope
, SS
);
4514 return NestedNameSpecifierLoc();
4516 QualType T
= TL
.getType();
4517 if (T
->isDependentType() || T
->isRecordType() ||
4518 (SemaRef
.getLangOpts().CPlusPlus11
&& T
->isEnumeralType())) {
4519 if (T
->isEnumeralType())
4520 SemaRef
.Diag(TL
.getBeginLoc(),
4521 diag::warn_cxx98_compat_enum_nested_name_spec
);
4523 if (const auto ETL
= TL
.getAs
<ElaboratedTypeLoc
>()) {
4524 SS
.Adopt(ETL
.getQualifierLoc());
4525 TL
= ETL
.getNamedTypeLoc();
4528 SS
.Extend(SemaRef
.Context
, TL
.getTemplateKeywordLoc(), TL
,
4529 Q
.getLocalEndLoc());
4532 // If the nested-name-specifier is an invalid type def, don't emit an
4533 // error because a previous error should have already been emitted.
4534 TypedefTypeLoc TTL
= TL
.getAsAdjusted
<TypedefTypeLoc
>();
4535 if (!TTL
|| !TTL
.getTypedefNameDecl()->isInvalidDecl()) {
4536 SemaRef
.Diag(TL
.getBeginLoc(), diag::err_nested_name_spec_non_tag
)
4537 << T
<< SS
.getRange();
4539 return NestedNameSpecifierLoc();
4543 // The qualifier-in-scope and object type only apply to the leftmost entity.
4544 FirstQualifierInScope
= nullptr;
4545 ObjectType
= QualType();
4548 // Don't rebuild the nested-name-specifier if we don't have to.
4549 if (SS
.getScopeRep() == NNS
.getNestedNameSpecifier() &&
4550 !getDerived().AlwaysRebuild())
4553 // If we can re-use the source-location data from the original
4554 // nested-name-specifier, do so.
4555 if (SS
.location_size() == NNS
.getDataLength() &&
4556 memcmp(SS
.location_data(), NNS
.getOpaqueData(), SS
.location_size()) == 0)
4557 return NestedNameSpecifierLoc(SS
.getScopeRep(), NNS
.getOpaqueData());
4559 // Allocate new nested-name-specifier location information.
4560 return SS
.getWithLocInContext(SemaRef
.Context
);
4563 template<typename Derived
>
4565 TreeTransform
<Derived
>
4566 ::TransformDeclarationNameInfo(const DeclarationNameInfo
&NameInfo
) {
4567 DeclarationName Name
= NameInfo
.getName();
4569 return DeclarationNameInfo();
4571 switch (Name
.getNameKind()) {
4572 case DeclarationName::Identifier
:
4573 case DeclarationName::ObjCZeroArgSelector
:
4574 case DeclarationName::ObjCOneArgSelector
:
4575 case DeclarationName::ObjCMultiArgSelector
:
4576 case DeclarationName::CXXOperatorName
:
4577 case DeclarationName::CXXLiteralOperatorName
:
4578 case DeclarationName::CXXUsingDirective
:
4581 case DeclarationName::CXXDeductionGuideName
: {
4582 TemplateDecl
*OldTemplate
= Name
.getCXXDeductionGuideTemplate();
4583 TemplateDecl
*NewTemplate
= cast_or_null
<TemplateDecl
>(
4584 getDerived().TransformDecl(NameInfo
.getLoc(), OldTemplate
));
4586 return DeclarationNameInfo();
4588 DeclarationNameInfo
NewNameInfo(NameInfo
);
4589 NewNameInfo
.setName(
4590 SemaRef
.Context
.DeclarationNames
.getCXXDeductionGuideName(NewTemplate
));
4594 case DeclarationName::CXXConstructorName
:
4595 case DeclarationName::CXXDestructorName
:
4596 case DeclarationName::CXXConversionFunctionName
: {
4597 TypeSourceInfo
*NewTInfo
;
4598 CanQualType NewCanTy
;
4599 if (TypeSourceInfo
*OldTInfo
= NameInfo
.getNamedTypeInfo()) {
4600 NewTInfo
= getDerived().TransformType(OldTInfo
);
4602 return DeclarationNameInfo();
4603 NewCanTy
= SemaRef
.Context
.getCanonicalType(NewTInfo
->getType());
4607 TemporaryBase
Rebase(*this, NameInfo
.getLoc(), Name
);
4608 QualType NewT
= getDerived().TransformType(Name
.getCXXNameType());
4610 return DeclarationNameInfo();
4611 NewCanTy
= SemaRef
.Context
.getCanonicalType(NewT
);
4614 DeclarationName NewName
4615 = SemaRef
.Context
.DeclarationNames
.getCXXSpecialName(Name
.getNameKind(),
4617 DeclarationNameInfo
NewNameInfo(NameInfo
);
4618 NewNameInfo
.setName(NewName
);
4619 NewNameInfo
.setNamedTypeInfo(NewTInfo
);
4624 llvm_unreachable("Unknown name kind.");
4627 template<typename Derived
>
4629 TreeTransform
<Derived
>::TransformTemplateName(CXXScopeSpec
&SS
,
4631 SourceLocation NameLoc
,
4632 QualType ObjectType
,
4633 NamedDecl
*FirstQualifierInScope
,
4634 bool AllowInjectedClassName
) {
4635 if (QualifiedTemplateName
*QTN
= Name
.getAsQualifiedTemplateName()) {
4636 TemplateDecl
*Template
= QTN
->getUnderlyingTemplate().getAsTemplateDecl();
4637 assert(Template
&& "qualified template name must refer to a template");
4639 TemplateDecl
*TransTemplate
4640 = cast_or_null
<TemplateDecl
>(getDerived().TransformDecl(NameLoc
,
4643 return TemplateName();
4645 if (!getDerived().AlwaysRebuild() &&
4646 SS
.getScopeRep() == QTN
->getQualifier() &&
4647 TransTemplate
== Template
)
4650 return getDerived().RebuildTemplateName(SS
, QTN
->hasTemplateKeyword(),
4654 if (DependentTemplateName
*DTN
= Name
.getAsDependentTemplateName()) {
4655 if (SS
.getScopeRep()) {
4656 // These apply to the scope specifier, not the template.
4657 ObjectType
= QualType();
4658 FirstQualifierInScope
= nullptr;
4661 if (!getDerived().AlwaysRebuild() &&
4662 SS
.getScopeRep() == DTN
->getQualifier() &&
4663 ObjectType
.isNull())
4666 // FIXME: Preserve the location of the "template" keyword.
4667 SourceLocation TemplateKWLoc
= NameLoc
;
4669 if (DTN
->isIdentifier()) {
4670 return getDerived().RebuildTemplateName(SS
,
4672 *DTN
->getIdentifier(),
4675 FirstQualifierInScope
,
4676 AllowInjectedClassName
);
4679 return getDerived().RebuildTemplateName(SS
, TemplateKWLoc
,
4680 DTN
->getOperator(), NameLoc
,
4681 ObjectType
, AllowInjectedClassName
);
4684 // FIXME: Try to preserve more of the TemplateName.
4685 if (TemplateDecl
*Template
= Name
.getAsTemplateDecl()) {
4686 TemplateDecl
*TransTemplate
4687 = cast_or_null
<TemplateDecl
>(getDerived().TransformDecl(NameLoc
,
4690 return TemplateName();
4692 return getDerived().RebuildTemplateName(SS
, /*TemplateKeyword=*/false,
4696 if (SubstTemplateTemplateParmPackStorage
*SubstPack
4697 = Name
.getAsSubstTemplateTemplateParmPack()) {
4698 return getDerived().RebuildTemplateName(
4699 SubstPack
->getArgumentPack(), SubstPack
->getAssociatedDecl(),
4700 SubstPack
->getIndex(), SubstPack
->getFinal());
4703 // These should be getting filtered out before they reach the AST.
4704 llvm_unreachable("overloaded function decl survived to here");
4707 template<typename Derived
>
4708 void TreeTransform
<Derived
>::InventTemplateArgumentLoc(
4709 const TemplateArgument
&Arg
,
4710 TemplateArgumentLoc
&Output
) {
4711 Output
= getSema().getTrivialTemplateArgumentLoc(
4712 Arg
, QualType(), getDerived().getBaseLocation());
4715 template <typename Derived
>
4716 bool TreeTransform
<Derived
>::TransformTemplateArgument(
4717 const TemplateArgumentLoc
&Input
, TemplateArgumentLoc
&Output
,
4719 const TemplateArgument
&Arg
= Input
.getArgument();
4720 switch (Arg
.getKind()) {
4721 case TemplateArgument::Null
:
4722 case TemplateArgument::Pack
:
4723 llvm_unreachable("Unexpected TemplateArgument");
4725 case TemplateArgument::Integral
:
4726 case TemplateArgument::NullPtr
:
4727 case TemplateArgument::Declaration
:
4728 case TemplateArgument::StructuralValue
: {
4729 // Transform a resolved template argument straight to a resolved template
4730 // argument. We get here when substituting into an already-substituted
4731 // template type argument during concept satisfaction checking.
4732 QualType T
= Arg
.getNonTypeTemplateArgumentType();
4733 QualType NewT
= getDerived().TransformType(T
);
4737 ValueDecl
*D
= Arg
.getKind() == TemplateArgument::Declaration
4740 ValueDecl
*NewD
= D
? cast_or_null
<ValueDecl
>(getDerived().TransformDecl(
4741 getDerived().getBaseLocation(), D
))
4746 if (NewT
== T
&& D
== NewD
)
4748 else if (Arg
.getKind() == TemplateArgument::Integral
)
4749 Output
= TemplateArgumentLoc(
4750 TemplateArgument(getSema().Context
, Arg
.getAsIntegral(), NewT
),
4751 TemplateArgumentLocInfo());
4752 else if (Arg
.getKind() == TemplateArgument::NullPtr
)
4753 Output
= TemplateArgumentLoc(TemplateArgument(NewT
, /*IsNullPtr=*/true),
4754 TemplateArgumentLocInfo());
4755 else if (Arg
.getKind() == TemplateArgument::Declaration
)
4756 Output
= TemplateArgumentLoc(TemplateArgument(NewD
, NewT
),
4757 TemplateArgumentLocInfo());
4758 else if (Arg
.getKind() == TemplateArgument::StructuralValue
)
4759 Output
= TemplateArgumentLoc(
4760 TemplateArgument(getSema().Context
, NewT
, Arg
.getAsStructuralValue()),
4761 TemplateArgumentLocInfo());
4763 llvm_unreachable("unexpected template argument kind");
4768 case TemplateArgument::Type
: {
4769 TypeSourceInfo
*DI
= Input
.getTypeSourceInfo();
4771 DI
= InventTypeSourceInfo(Input
.getArgument().getAsType());
4773 DI
= getDerived().TransformType(DI
);
4777 Output
= TemplateArgumentLoc(TemplateArgument(DI
->getType()), DI
);
4781 case TemplateArgument::Template
: {
4782 NestedNameSpecifierLoc QualifierLoc
= Input
.getTemplateQualifierLoc();
4784 QualifierLoc
= getDerived().TransformNestedNameSpecifierLoc(QualifierLoc
);
4790 SS
.Adopt(QualifierLoc
);
4791 TemplateName Template
= getDerived().TransformTemplateName(
4792 SS
, Arg
.getAsTemplate(), Input
.getTemplateNameLoc());
4793 if (Template
.isNull())
4796 Output
= TemplateArgumentLoc(SemaRef
.Context
, TemplateArgument(Template
),
4797 QualifierLoc
, Input
.getTemplateNameLoc());
4801 case TemplateArgument::TemplateExpansion
:
4802 llvm_unreachable("Caller should expand pack expansions");
4804 case TemplateArgument::Expression
: {
4805 // Template argument expressions are constant expressions.
4806 EnterExpressionEvaluationContext
Unevaluated(
4808 Uneval
? Sema::ExpressionEvaluationContext::Unevaluated
4809 : Sema::ExpressionEvaluationContext::ConstantEvaluated
,
4810 Sema::ReuseLambdaContextDecl
, /*ExprContext=*/
4811 Sema::ExpressionEvaluationContextRecord::EK_TemplateArgument
);
4813 Expr
*InputExpr
= Input
.getSourceExpression();
4815 InputExpr
= Input
.getArgument().getAsExpr();
4817 ExprResult E
= getDerived().TransformExpr(InputExpr
);
4818 E
= SemaRef
.ActOnConstantExpression(E
);
4821 Output
= TemplateArgumentLoc(TemplateArgument(E
.get()), E
.get());
4826 // Work around bogus GCC warning
4830 /// Iterator adaptor that invents template argument location information
4831 /// for each of the template arguments in its underlying iterator.
4832 template<typename Derived
, typename InputIterator
>
4833 class TemplateArgumentLocInventIterator
{
4834 TreeTransform
<Derived
> &Self
;
4838 typedef TemplateArgumentLoc value_type
;
4839 typedef TemplateArgumentLoc reference
;
4840 typedef typename
std::iterator_traits
<InputIterator
>::difference_type
4842 typedef std::input_iterator_tag iterator_category
;
4845 TemplateArgumentLoc Arg
;
4848 explicit pointer(TemplateArgumentLoc Arg
) : Arg(Arg
) { }
4850 const TemplateArgumentLoc
*operator->() const { return &Arg
; }
4853 explicit TemplateArgumentLocInventIterator(TreeTransform
<Derived
> &Self
,
4855 : Self(Self
), Iter(Iter
) { }
4857 TemplateArgumentLocInventIterator
&operator++() {
4862 TemplateArgumentLocInventIterator
operator++(int) {
4863 TemplateArgumentLocInventIterator
Old(*this);
4868 reference
operator*() const {
4869 TemplateArgumentLoc Result
;
4870 Self
.InventTemplateArgumentLoc(*Iter
, Result
);
4874 pointer
operator->() const { return pointer(**this); }
4876 friend bool operator==(const TemplateArgumentLocInventIterator
&X
,
4877 const TemplateArgumentLocInventIterator
&Y
) {
4878 return X
.Iter
== Y
.Iter
;
4881 friend bool operator!=(const TemplateArgumentLocInventIterator
&X
,
4882 const TemplateArgumentLocInventIterator
&Y
) {
4883 return X
.Iter
!= Y
.Iter
;
4887 template<typename Derived
>
4888 template<typename InputIterator
>
4889 bool TreeTransform
<Derived
>::TransformTemplateArguments(
4890 InputIterator First
, InputIterator Last
, TemplateArgumentListInfo
&Outputs
,
4892 for (; First
!= Last
; ++First
) {
4893 TemplateArgumentLoc Out
;
4894 TemplateArgumentLoc In
= *First
;
4896 if (In
.getArgument().getKind() == TemplateArgument::Pack
) {
4897 // Unpack argument packs, which we translate them into separate
4899 // FIXME: We could do much better if we could guarantee that the
4900 // TemplateArgumentLocInfo for the pack expansion would be usable for
4901 // all of the template arguments in the argument pack.
4902 typedef TemplateArgumentLocInventIterator
<Derived
,
4903 TemplateArgument::pack_iterator
>
4905 if (TransformTemplateArguments(PackLocIterator(*this,
4906 In
.getArgument().pack_begin()),
4907 PackLocIterator(*this,
4908 In
.getArgument().pack_end()),
4915 if (In
.getArgument().isPackExpansion()) {
4916 // We have a pack expansion, for which we will be substituting into
4918 SourceLocation Ellipsis
;
4919 std::optional
<unsigned> OrigNumExpansions
;
4920 TemplateArgumentLoc Pattern
4921 = getSema().getTemplateArgumentPackExpansionPattern(
4922 In
, Ellipsis
, OrigNumExpansions
);
4924 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
4925 getSema().collectUnexpandedParameterPacks(Pattern
, Unexpanded
);
4926 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
4928 // Determine whether the set of unexpanded parameter packs can and should
4931 bool RetainExpansion
= false;
4932 std::optional
<unsigned> NumExpansions
= OrigNumExpansions
;
4933 if (getDerived().TryExpandParameterPacks(Ellipsis
,
4934 Pattern
.getSourceRange(),
4942 // The transform has determined that we should perform a simple
4943 // transformation on the pack expansion, producing another pack
4945 TemplateArgumentLoc OutPattern
;
4946 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
4947 if (getDerived().TransformTemplateArgument(Pattern
, OutPattern
, Uneval
))
4950 Out
= getDerived().RebuildPackExpansion(OutPattern
, Ellipsis
,
4952 if (Out
.getArgument().isNull())
4955 Outputs
.addArgument(Out
);
4959 // The transform has determined that we should perform an elementwise
4960 // expansion of the pattern. Do so.
4961 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
4962 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
4964 if (getDerived().TransformTemplateArgument(Pattern
, Out
, Uneval
))
4967 if (Out
.getArgument().containsUnexpandedParameterPack()) {
4968 Out
= getDerived().RebuildPackExpansion(Out
, Ellipsis
,
4970 if (Out
.getArgument().isNull())
4974 Outputs
.addArgument(Out
);
4977 // If we're supposed to retain a pack expansion, do so by temporarily
4978 // forgetting the partially-substituted parameter pack.
4979 if (RetainExpansion
) {
4980 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
4982 if (getDerived().TransformTemplateArgument(Pattern
, Out
, Uneval
))
4985 Out
= getDerived().RebuildPackExpansion(Out
, Ellipsis
,
4987 if (Out
.getArgument().isNull())
4990 Outputs
.addArgument(Out
);
4997 if (getDerived().TransformTemplateArgument(In
, Out
, Uneval
))
5000 Outputs
.addArgument(Out
);
5007 //===----------------------------------------------------------------------===//
5008 // Type transformation
5009 //===----------------------------------------------------------------------===//
5011 template<typename Derived
>
5012 QualType TreeTransform
<Derived
>::TransformType(QualType T
) {
5013 if (getDerived().AlreadyTransformed(T
))
5016 // Temporary workaround. All of these transformations should
5017 // eventually turn into transformations on TypeLocs.
5018 TypeSourceInfo
*DI
= getSema().Context
.getTrivialTypeSourceInfo(T
,
5019 getDerived().getBaseLocation());
5021 TypeSourceInfo
*NewDI
= getDerived().TransformType(DI
);
5026 return NewDI
->getType();
5029 template<typename Derived
>
5030 TypeSourceInfo
*TreeTransform
<Derived
>::TransformType(TypeSourceInfo
*DI
) {
5031 // Refine the base location to the type's location.
5032 TemporaryBase
Rebase(*this, DI
->getTypeLoc().getBeginLoc(),
5033 getDerived().getBaseEntity());
5034 if (getDerived().AlreadyTransformed(DI
->getType()))
5039 TypeLoc TL
= DI
->getTypeLoc();
5040 TLB
.reserve(TL
.getFullDataSize());
5042 QualType Result
= getDerived().TransformType(TLB
, TL
);
5043 if (Result
.isNull())
5046 return TLB
.getTypeSourceInfo(SemaRef
.Context
, Result
);
5049 template<typename Derived
>
5051 TreeTransform
<Derived
>::TransformType(TypeLocBuilder
&TLB
, TypeLoc T
) {
5052 switch (T
.getTypeLocClass()) {
5053 #define ABSTRACT_TYPELOC(CLASS, PARENT)
5054 #define TYPELOC(CLASS, PARENT) \
5055 case TypeLoc::CLASS: \
5056 return getDerived().Transform##CLASS##Type(TLB, \
5057 T.castAs<CLASS##TypeLoc>());
5058 #include "clang/AST/TypeLocNodes.def"
5061 llvm_unreachable("unhandled type loc!");
5064 template<typename Derived
>
5065 QualType TreeTransform
<Derived
>::TransformTypeWithDeducedTST(QualType T
) {
5066 if (!isa
<DependentNameType
>(T
))
5067 return TransformType(T
);
5069 if (getDerived().AlreadyTransformed(T
))
5071 TypeSourceInfo
*DI
= getSema().Context
.getTrivialTypeSourceInfo(T
,
5072 getDerived().getBaseLocation());
5073 TypeSourceInfo
*NewDI
= getDerived().TransformTypeWithDeducedTST(DI
);
5074 return NewDI
? NewDI
->getType() : QualType();
5077 template<typename Derived
>
5079 TreeTransform
<Derived
>::TransformTypeWithDeducedTST(TypeSourceInfo
*DI
) {
5080 if (!isa
<DependentNameType
>(DI
->getType()))
5081 return TransformType(DI
);
5083 // Refine the base location to the type's location.
5084 TemporaryBase
Rebase(*this, DI
->getTypeLoc().getBeginLoc(),
5085 getDerived().getBaseEntity());
5086 if (getDerived().AlreadyTransformed(DI
->getType()))
5091 TypeLoc TL
= DI
->getTypeLoc();
5092 TLB
.reserve(TL
.getFullDataSize());
5094 auto QTL
= TL
.getAs
<QualifiedTypeLoc
>();
5096 TL
= QTL
.getUnqualifiedLoc();
5098 auto DNTL
= TL
.castAs
<DependentNameTypeLoc
>();
5100 QualType Result
= getDerived().TransformDependentNameType(
5101 TLB
, DNTL
, /*DeducedTSTContext*/true);
5102 if (Result
.isNull())
5106 Result
= getDerived().RebuildQualifiedType(Result
, QTL
);
5107 if (Result
.isNull())
5109 TLB
.TypeWasModifiedSafely(Result
);
5112 return TLB
.getTypeSourceInfo(SemaRef
.Context
, Result
);
5115 template<typename Derived
>
5117 TreeTransform
<Derived
>::TransformQualifiedType(TypeLocBuilder
&TLB
,
5118 QualifiedTypeLoc T
) {
5120 TypeLoc UnqualTL
= T
.getUnqualifiedLoc();
5121 auto SuppressObjCLifetime
=
5122 T
.getType().getLocalQualifiers().hasObjCLifetime();
5123 if (auto TTP
= UnqualTL
.getAs
<TemplateTypeParmTypeLoc
>()) {
5124 Result
= getDerived().TransformTemplateTypeParmType(TLB
, TTP
,
5125 SuppressObjCLifetime
);
5126 } else if (auto STTP
= UnqualTL
.getAs
<SubstTemplateTypeParmPackTypeLoc
>()) {
5127 Result
= getDerived().TransformSubstTemplateTypeParmPackType(
5128 TLB
, STTP
, SuppressObjCLifetime
);
5130 Result
= getDerived().TransformType(TLB
, UnqualTL
);
5133 if (Result
.isNull())
5136 Result
= getDerived().RebuildQualifiedType(Result
, T
);
5138 if (Result
.isNull())
5141 // RebuildQualifiedType might have updated the type, but not in a way
5142 // that invalidates the TypeLoc. (There's no location information for
5144 TLB
.TypeWasModifiedSafely(Result
);
5149 template <typename Derived
>
5150 QualType TreeTransform
<Derived
>::RebuildQualifiedType(QualType T
,
5151 QualifiedTypeLoc TL
) {
5153 SourceLocation Loc
= TL
.getBeginLoc();
5154 Qualifiers Quals
= TL
.getType().getLocalQualifiers();
5156 if ((T
.getAddressSpace() != LangAS::Default
&&
5157 Quals
.getAddressSpace() != LangAS::Default
) &&
5158 T
.getAddressSpace() != Quals
.getAddressSpace()) {
5159 SemaRef
.Diag(Loc
, diag::err_address_space_mismatch_templ_inst
)
5160 << TL
.getType() << T
;
5165 // [When] adding cv-qualifications on top of the function type [...] the
5166 // cv-qualifiers are ignored.
5167 if (T
->isFunctionType()) {
5168 T
= SemaRef
.getASTContext().getAddrSpaceQualType(T
,
5169 Quals
.getAddressSpace());
5174 // when the cv-qualifiers are introduced through the use of a typedef-name
5175 // or decltype-specifier [...] the cv-qualifiers are ignored.
5176 // Note that [dcl.ref]p1 lists all cases in which cv-qualifiers can be
5177 // applied to a reference type.
5178 if (T
->isReferenceType()) {
5179 // The only qualifier that applies to a reference type is restrict.
5180 if (!Quals
.hasRestrict())
5182 Quals
= Qualifiers::fromCVRMask(Qualifiers::Restrict
);
5185 // Suppress Objective-C lifetime qualifiers if they don't make sense for the
5187 if (Quals
.hasObjCLifetime()) {
5188 if (!T
->isObjCLifetimeType() && !T
->isDependentType())
5189 Quals
.removeObjCLifetime();
5190 else if (T
.getObjCLifetime()) {
5192 // A lifetime qualifier applied to a substituted template parameter
5193 // overrides the lifetime qualifier from the template argument.
5194 const AutoType
*AutoTy
;
5195 if ((AutoTy
= dyn_cast
<AutoType
>(T
)) && AutoTy
->isDeduced()) {
5196 // 'auto' types behave the same way as template parameters.
5197 QualType Deduced
= AutoTy
->getDeducedType();
5198 Qualifiers Qs
= Deduced
.getQualifiers();
5199 Qs
.removeObjCLifetime();
5201 SemaRef
.Context
.getQualifiedType(Deduced
.getUnqualifiedType(), Qs
);
5202 T
= SemaRef
.Context
.getAutoType(Deduced
, AutoTy
->getKeyword(),
5203 AutoTy
->isDependentType(),
5205 AutoTy
->getTypeConstraintConcept(),
5206 AutoTy
->getTypeConstraintArguments());
5208 // Otherwise, complain about the addition of a qualifier to an
5209 // already-qualified type.
5210 // FIXME: Why is this check not in Sema::BuildQualifiedType?
5211 SemaRef
.Diag(Loc
, diag::err_attr_objc_ownership_redundant
) << T
;
5212 Quals
.removeObjCLifetime();
5217 return SemaRef
.BuildQualifiedType(T
, Loc
, Quals
);
5220 template<typename Derived
>
5222 TreeTransform
<Derived
>::TransformTypeInObjectScope(TypeLoc TL
,
5223 QualType ObjectType
,
5224 NamedDecl
*UnqualLookup
,
5226 if (getDerived().AlreadyTransformed(TL
.getType()))
5229 TypeSourceInfo
*TSI
=
5230 TransformTSIInObjectScope(TL
, ObjectType
, UnqualLookup
, SS
);
5232 return TSI
->getTypeLoc();
5236 template<typename Derived
>
5238 TreeTransform
<Derived
>::TransformTypeInObjectScope(TypeSourceInfo
*TSInfo
,
5239 QualType ObjectType
,
5240 NamedDecl
*UnqualLookup
,
5242 if (getDerived().AlreadyTransformed(TSInfo
->getType()))
5245 return TransformTSIInObjectScope(TSInfo
->getTypeLoc(), ObjectType
,
5249 template <typename Derived
>
5250 TypeSourceInfo
*TreeTransform
<Derived
>::TransformTSIInObjectScope(
5251 TypeLoc TL
, QualType ObjectType
, NamedDecl
*UnqualLookup
,
5253 QualType T
= TL
.getType();
5254 assert(!getDerived().AlreadyTransformed(T
));
5259 if (isa
<TemplateSpecializationType
>(T
)) {
5260 TemplateSpecializationTypeLoc SpecTL
=
5261 TL
.castAs
<TemplateSpecializationTypeLoc
>();
5263 TemplateName Template
= getDerived().TransformTemplateName(
5264 SS
, SpecTL
.getTypePtr()->getTemplateName(), SpecTL
.getTemplateNameLoc(),
5265 ObjectType
, UnqualLookup
, /*AllowInjectedClassName*/true);
5266 if (Template
.isNull())
5269 Result
= getDerived().TransformTemplateSpecializationType(TLB
, SpecTL
,
5271 } else if (isa
<DependentTemplateSpecializationType
>(T
)) {
5272 DependentTemplateSpecializationTypeLoc SpecTL
=
5273 TL
.castAs
<DependentTemplateSpecializationTypeLoc
>();
5275 TemplateName Template
5276 = getDerived().RebuildTemplateName(SS
,
5277 SpecTL
.getTemplateKeywordLoc(),
5278 *SpecTL
.getTypePtr()->getIdentifier(),
5279 SpecTL
.getTemplateNameLoc(),
5280 ObjectType
, UnqualLookup
,
5281 /*AllowInjectedClassName*/true);
5282 if (Template
.isNull())
5285 Result
= getDerived().TransformDependentTemplateSpecializationType(TLB
,
5290 // Nothing special needs to be done for these.
5291 Result
= getDerived().TransformType(TLB
, TL
);
5294 if (Result
.isNull())
5297 return TLB
.getTypeSourceInfo(SemaRef
.Context
, Result
);
5300 template <class TyLoc
> static inline
5301 QualType
TransformTypeSpecType(TypeLocBuilder
&TLB
, TyLoc T
) {
5302 TyLoc NewT
= TLB
.push
<TyLoc
>(T
.getType());
5303 NewT
.setNameLoc(T
.getNameLoc());
5307 template<typename Derived
>
5308 QualType TreeTransform
<Derived
>::TransformBuiltinType(TypeLocBuilder
&TLB
,
5310 BuiltinTypeLoc NewT
= TLB
.push
<BuiltinTypeLoc
>(T
.getType());
5311 NewT
.setBuiltinLoc(T
.getBuiltinLoc());
5312 if (T
.needsExtraLocalData())
5313 NewT
.getWrittenBuiltinSpecs() = T
.getWrittenBuiltinSpecs();
5317 template<typename Derived
>
5318 QualType TreeTransform
<Derived
>::TransformComplexType(TypeLocBuilder
&TLB
,
5321 return TransformTypeSpecType(TLB
, T
);
5324 template <typename Derived
>
5325 QualType TreeTransform
<Derived
>::TransformAdjustedType(TypeLocBuilder
&TLB
,
5326 AdjustedTypeLoc TL
) {
5327 // Adjustments applied during transformation are handled elsewhere.
5328 return getDerived().TransformType(TLB
, TL
.getOriginalLoc());
5331 template<typename Derived
>
5332 QualType TreeTransform
<Derived
>::TransformDecayedType(TypeLocBuilder
&TLB
,
5333 DecayedTypeLoc TL
) {
5334 QualType OriginalType
= getDerived().TransformType(TLB
, TL
.getOriginalLoc());
5335 if (OriginalType
.isNull())
5338 QualType Result
= TL
.getType();
5339 if (getDerived().AlwaysRebuild() ||
5340 OriginalType
!= TL
.getOriginalLoc().getType())
5341 Result
= SemaRef
.Context
.getDecayedType(OriginalType
);
5342 TLB
.push
<DecayedTypeLoc
>(Result
);
5343 // Nothing to set for DecayedTypeLoc.
5347 template <typename Derived
>
5349 TreeTransform
<Derived
>::TransformArrayParameterType(TypeLocBuilder
&TLB
,
5350 ArrayParameterTypeLoc TL
) {
5351 QualType OriginalType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5352 if (OriginalType
.isNull())
5355 QualType Result
= TL
.getType();
5356 if (getDerived().AlwaysRebuild() ||
5357 OriginalType
!= TL
.getElementLoc().getType())
5358 Result
= SemaRef
.Context
.getArrayParameterType(OriginalType
);
5359 TLB
.push
<ArrayParameterTypeLoc
>(Result
);
5360 // Nothing to set for ArrayParameterTypeLoc.
5364 template<typename Derived
>
5365 QualType TreeTransform
<Derived
>::TransformPointerType(TypeLocBuilder
&TLB
,
5366 PointerTypeLoc TL
) {
5367 QualType PointeeType
5368 = getDerived().TransformType(TLB
, TL
.getPointeeLoc());
5369 if (PointeeType
.isNull())
5372 QualType Result
= TL
.getType();
5373 if (PointeeType
->getAs
<ObjCObjectType
>()) {
5374 // A dependent pointer type 'T *' has is being transformed such
5375 // that an Objective-C class type is being replaced for 'T'. The
5376 // resulting pointer type is an ObjCObjectPointerType, not a
5378 Result
= SemaRef
.Context
.getObjCObjectPointerType(PointeeType
);
5380 ObjCObjectPointerTypeLoc NewT
= TLB
.push
<ObjCObjectPointerTypeLoc
>(Result
);
5381 NewT
.setStarLoc(TL
.getStarLoc());
5385 if (getDerived().AlwaysRebuild() ||
5386 PointeeType
!= TL
.getPointeeLoc().getType()) {
5387 Result
= getDerived().RebuildPointerType(PointeeType
, TL
.getSigilLoc());
5388 if (Result
.isNull())
5392 // Objective-C ARC can add lifetime qualifiers to the type that we're
5394 TLB
.TypeWasModifiedSafely(Result
->getPointeeType());
5396 PointerTypeLoc NewT
= TLB
.push
<PointerTypeLoc
>(Result
);
5397 NewT
.setSigilLoc(TL
.getSigilLoc());
5401 template<typename Derived
>
5403 TreeTransform
<Derived
>::TransformBlockPointerType(TypeLocBuilder
&TLB
,
5404 BlockPointerTypeLoc TL
) {
5405 QualType PointeeType
5406 = getDerived().TransformType(TLB
, TL
.getPointeeLoc());
5407 if (PointeeType
.isNull())
5410 QualType Result
= TL
.getType();
5411 if (getDerived().AlwaysRebuild() ||
5412 PointeeType
!= TL
.getPointeeLoc().getType()) {
5413 Result
= getDerived().RebuildBlockPointerType(PointeeType
,
5415 if (Result
.isNull())
5419 BlockPointerTypeLoc NewT
= TLB
.push
<BlockPointerTypeLoc
>(Result
);
5420 NewT
.setSigilLoc(TL
.getSigilLoc());
5424 /// Transforms a reference type. Note that somewhat paradoxically we
5425 /// don't care whether the type itself is an l-value type or an r-value
5426 /// type; we only care if the type was *written* as an l-value type
5427 /// or an r-value type.
5428 template<typename Derived
>
5430 TreeTransform
<Derived
>::TransformReferenceType(TypeLocBuilder
&TLB
,
5431 ReferenceTypeLoc TL
) {
5432 const ReferenceType
*T
= TL
.getTypePtr();
5434 // Note that this works with the pointee-as-written.
5435 QualType PointeeType
= getDerived().TransformType(TLB
, TL
.getPointeeLoc());
5436 if (PointeeType
.isNull())
5439 QualType Result
= TL
.getType();
5440 if (getDerived().AlwaysRebuild() ||
5441 PointeeType
!= T
->getPointeeTypeAsWritten()) {
5442 Result
= getDerived().RebuildReferenceType(PointeeType
,
5443 T
->isSpelledAsLValue(),
5445 if (Result
.isNull())
5449 // Objective-C ARC can add lifetime qualifiers to the type that we're
5451 TLB
.TypeWasModifiedSafely(
5452 Result
->castAs
<ReferenceType
>()->getPointeeTypeAsWritten());
5454 // r-value references can be rebuilt as l-value references.
5455 ReferenceTypeLoc NewTL
;
5456 if (isa
<LValueReferenceType
>(Result
))
5457 NewTL
= TLB
.push
<LValueReferenceTypeLoc
>(Result
);
5459 NewTL
= TLB
.push
<RValueReferenceTypeLoc
>(Result
);
5460 NewTL
.setSigilLoc(TL
.getSigilLoc());
5465 template<typename Derived
>
5467 TreeTransform
<Derived
>::TransformLValueReferenceType(TypeLocBuilder
&TLB
,
5468 LValueReferenceTypeLoc TL
) {
5469 return TransformReferenceType(TLB
, TL
);
5472 template<typename Derived
>
5474 TreeTransform
<Derived
>::TransformRValueReferenceType(TypeLocBuilder
&TLB
,
5475 RValueReferenceTypeLoc TL
) {
5476 return TransformReferenceType(TLB
, TL
);
5479 template<typename Derived
>
5481 TreeTransform
<Derived
>::TransformMemberPointerType(TypeLocBuilder
&TLB
,
5482 MemberPointerTypeLoc TL
) {
5483 QualType PointeeType
= getDerived().TransformType(TLB
, TL
.getPointeeLoc());
5484 if (PointeeType
.isNull())
5487 TypeSourceInfo
* OldClsTInfo
= TL
.getClassTInfo();
5488 TypeSourceInfo
*NewClsTInfo
= nullptr;
5490 NewClsTInfo
= getDerived().TransformType(OldClsTInfo
);
5495 const MemberPointerType
*T
= TL
.getTypePtr();
5496 QualType OldClsType
= QualType(T
->getClass(), 0);
5497 QualType NewClsType
;
5499 NewClsType
= NewClsTInfo
->getType();
5501 NewClsType
= getDerived().TransformType(OldClsType
);
5502 if (NewClsType
.isNull())
5506 QualType Result
= TL
.getType();
5507 if (getDerived().AlwaysRebuild() ||
5508 PointeeType
!= T
->getPointeeType() ||
5509 NewClsType
!= OldClsType
) {
5510 Result
= getDerived().RebuildMemberPointerType(PointeeType
, NewClsType
,
5512 if (Result
.isNull())
5516 // If we had to adjust the pointee type when building a member pointer, make
5517 // sure to push TypeLoc info for it.
5518 const MemberPointerType
*MPT
= Result
->getAs
<MemberPointerType
>();
5519 if (MPT
&& PointeeType
!= MPT
->getPointeeType()) {
5520 assert(isa
<AdjustedType
>(MPT
->getPointeeType()));
5521 TLB
.push
<AdjustedTypeLoc
>(MPT
->getPointeeType());
5524 MemberPointerTypeLoc NewTL
= TLB
.push
<MemberPointerTypeLoc
>(Result
);
5525 NewTL
.setSigilLoc(TL
.getSigilLoc());
5526 NewTL
.setClassTInfo(NewClsTInfo
);
5531 template<typename Derived
>
5533 TreeTransform
<Derived
>::TransformConstantArrayType(TypeLocBuilder
&TLB
,
5534 ConstantArrayTypeLoc TL
) {
5535 const ConstantArrayType
*T
= TL
.getTypePtr();
5536 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5537 if (ElementType
.isNull())
5540 // Prefer the expression from the TypeLoc; the other may have been uniqued.
5541 Expr
*OldSize
= TL
.getSizeExpr();
5543 OldSize
= const_cast<Expr
*>(T
->getSizeExpr());
5544 Expr
*NewSize
= nullptr;
5546 EnterExpressionEvaluationContext
Unevaluated(
5547 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
5548 NewSize
= getDerived().TransformExpr(OldSize
).template getAs
<Expr
>();
5549 NewSize
= SemaRef
.ActOnConstantExpression(NewSize
).get();
5552 QualType Result
= TL
.getType();
5553 if (getDerived().AlwaysRebuild() ||
5554 ElementType
!= T
->getElementType() ||
5555 (T
->getSizeExpr() && NewSize
!= OldSize
)) {
5556 Result
= getDerived().RebuildConstantArrayType(ElementType
,
5557 T
->getSizeModifier(),
5558 T
->getSize(), NewSize
,
5559 T
->getIndexTypeCVRQualifiers(),
5560 TL
.getBracketsRange());
5561 if (Result
.isNull())
5565 // We might have either a ConstantArrayType or a VariableArrayType now:
5566 // a ConstantArrayType is allowed to have an element type which is a
5567 // VariableArrayType if the type is dependent. Fortunately, all array
5568 // types have the same location layout.
5569 ArrayTypeLoc NewTL
= TLB
.push
<ArrayTypeLoc
>(Result
);
5570 NewTL
.setLBracketLoc(TL
.getLBracketLoc());
5571 NewTL
.setRBracketLoc(TL
.getRBracketLoc());
5572 NewTL
.setSizeExpr(NewSize
);
5577 template<typename Derived
>
5578 QualType TreeTransform
<Derived
>::TransformIncompleteArrayType(
5579 TypeLocBuilder
&TLB
,
5580 IncompleteArrayTypeLoc TL
) {
5581 const IncompleteArrayType
*T
= TL
.getTypePtr();
5582 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5583 if (ElementType
.isNull())
5586 QualType Result
= TL
.getType();
5587 if (getDerived().AlwaysRebuild() ||
5588 ElementType
!= T
->getElementType()) {
5589 Result
= getDerived().RebuildIncompleteArrayType(ElementType
,
5590 T
->getSizeModifier(),
5591 T
->getIndexTypeCVRQualifiers(),
5592 TL
.getBracketsRange());
5593 if (Result
.isNull())
5597 IncompleteArrayTypeLoc NewTL
= TLB
.push
<IncompleteArrayTypeLoc
>(Result
);
5598 NewTL
.setLBracketLoc(TL
.getLBracketLoc());
5599 NewTL
.setRBracketLoc(TL
.getRBracketLoc());
5600 NewTL
.setSizeExpr(nullptr);
5605 template<typename Derived
>
5607 TreeTransform
<Derived
>::TransformVariableArrayType(TypeLocBuilder
&TLB
,
5608 VariableArrayTypeLoc TL
) {
5609 const VariableArrayType
*T
= TL
.getTypePtr();
5610 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5611 if (ElementType
.isNull())
5614 ExprResult SizeResult
;
5616 EnterExpressionEvaluationContext
Context(
5617 SemaRef
, Sema::ExpressionEvaluationContext::PotentiallyEvaluated
);
5618 SizeResult
= getDerived().TransformExpr(T
->getSizeExpr());
5620 if (SizeResult
.isInvalid())
5623 SemaRef
.ActOnFinishFullExpr(SizeResult
.get(), /*DiscardedValue*/ false);
5624 if (SizeResult
.isInvalid())
5627 Expr
*Size
= SizeResult
.get();
5629 QualType Result
= TL
.getType();
5630 if (getDerived().AlwaysRebuild() ||
5631 ElementType
!= T
->getElementType() ||
5632 Size
!= T
->getSizeExpr()) {
5633 Result
= getDerived().RebuildVariableArrayType(ElementType
,
5634 T
->getSizeModifier(),
5636 T
->getIndexTypeCVRQualifiers(),
5637 TL
.getBracketsRange());
5638 if (Result
.isNull())
5642 // We might have constant size array now, but fortunately it has the same
5644 ArrayTypeLoc NewTL
= TLB
.push
<ArrayTypeLoc
>(Result
);
5645 NewTL
.setLBracketLoc(TL
.getLBracketLoc());
5646 NewTL
.setRBracketLoc(TL
.getRBracketLoc());
5647 NewTL
.setSizeExpr(Size
);
5652 template<typename Derived
>
5654 TreeTransform
<Derived
>::TransformDependentSizedArrayType(TypeLocBuilder
&TLB
,
5655 DependentSizedArrayTypeLoc TL
) {
5656 const DependentSizedArrayType
*T
= TL
.getTypePtr();
5657 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5658 if (ElementType
.isNull())
5661 // Array bounds are constant expressions.
5662 EnterExpressionEvaluationContext
Unevaluated(
5663 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
5665 // If we have a VLA then it won't be a constant.
5666 SemaRef
.ExprEvalContexts
.back().InConditionallyConstantEvaluateContext
= true;
5668 // Prefer the expression from the TypeLoc; the other may have been uniqued.
5669 Expr
*origSize
= TL
.getSizeExpr();
5670 if (!origSize
) origSize
= T
->getSizeExpr();
5672 ExprResult sizeResult
5673 = getDerived().TransformExpr(origSize
);
5674 sizeResult
= SemaRef
.ActOnConstantExpression(sizeResult
);
5675 if (sizeResult
.isInvalid())
5678 Expr
*size
= sizeResult
.get();
5680 QualType Result
= TL
.getType();
5681 if (getDerived().AlwaysRebuild() ||
5682 ElementType
!= T
->getElementType() ||
5684 Result
= getDerived().RebuildDependentSizedArrayType(ElementType
,
5685 T
->getSizeModifier(),
5687 T
->getIndexTypeCVRQualifiers(),
5688 TL
.getBracketsRange());
5689 if (Result
.isNull())
5693 // We might have any sort of array type now, but fortunately they
5694 // all have the same location layout.
5695 ArrayTypeLoc NewTL
= TLB
.push
<ArrayTypeLoc
>(Result
);
5696 NewTL
.setLBracketLoc(TL
.getLBracketLoc());
5697 NewTL
.setRBracketLoc(TL
.getRBracketLoc());
5698 NewTL
.setSizeExpr(size
);
5703 template <typename Derived
>
5704 QualType TreeTransform
<Derived
>::TransformDependentVectorType(
5705 TypeLocBuilder
&TLB
, DependentVectorTypeLoc TL
) {
5706 const DependentVectorType
*T
= TL
.getTypePtr();
5707 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5708 if (ElementType
.isNull())
5711 EnterExpressionEvaluationContext
Unevaluated(
5712 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
5714 ExprResult Size
= getDerived().TransformExpr(T
->getSizeExpr());
5715 Size
= SemaRef
.ActOnConstantExpression(Size
);
5716 if (Size
.isInvalid())
5719 QualType Result
= TL
.getType();
5720 if (getDerived().AlwaysRebuild() || ElementType
!= T
->getElementType() ||
5721 Size
.get() != T
->getSizeExpr()) {
5722 Result
= getDerived().RebuildDependentVectorType(
5723 ElementType
, Size
.get(), T
->getAttributeLoc(), T
->getVectorKind());
5724 if (Result
.isNull())
5728 // Result might be dependent or not.
5729 if (isa
<DependentVectorType
>(Result
)) {
5730 DependentVectorTypeLoc NewTL
=
5731 TLB
.push
<DependentVectorTypeLoc
>(Result
);
5732 NewTL
.setNameLoc(TL
.getNameLoc());
5734 VectorTypeLoc NewTL
= TLB
.push
<VectorTypeLoc
>(Result
);
5735 NewTL
.setNameLoc(TL
.getNameLoc());
5741 template<typename Derived
>
5742 QualType TreeTransform
<Derived
>::TransformDependentSizedExtVectorType(
5743 TypeLocBuilder
&TLB
,
5744 DependentSizedExtVectorTypeLoc TL
) {
5745 const DependentSizedExtVectorType
*T
= TL
.getTypePtr();
5747 // FIXME: ext vector locs should be nested
5748 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5749 if (ElementType
.isNull())
5752 // Vector sizes are constant expressions.
5753 EnterExpressionEvaluationContext
Unevaluated(
5754 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
5756 ExprResult Size
= getDerived().TransformExpr(T
->getSizeExpr());
5757 Size
= SemaRef
.ActOnConstantExpression(Size
);
5758 if (Size
.isInvalid())
5761 QualType Result
= TL
.getType();
5762 if (getDerived().AlwaysRebuild() ||
5763 ElementType
!= T
->getElementType() ||
5764 Size
.get() != T
->getSizeExpr()) {
5765 Result
= getDerived().RebuildDependentSizedExtVectorType(ElementType
,
5767 T
->getAttributeLoc());
5768 if (Result
.isNull())
5772 // Result might be dependent or not.
5773 if (isa
<DependentSizedExtVectorType
>(Result
)) {
5774 DependentSizedExtVectorTypeLoc NewTL
5775 = TLB
.push
<DependentSizedExtVectorTypeLoc
>(Result
);
5776 NewTL
.setNameLoc(TL
.getNameLoc());
5778 ExtVectorTypeLoc NewTL
= TLB
.push
<ExtVectorTypeLoc
>(Result
);
5779 NewTL
.setNameLoc(TL
.getNameLoc());
5785 template <typename Derived
>
5787 TreeTransform
<Derived
>::TransformConstantMatrixType(TypeLocBuilder
&TLB
,
5788 ConstantMatrixTypeLoc TL
) {
5789 const ConstantMatrixType
*T
= TL
.getTypePtr();
5790 QualType ElementType
= getDerived().TransformType(T
->getElementType());
5791 if (ElementType
.isNull())
5794 QualType Result
= TL
.getType();
5795 if (getDerived().AlwaysRebuild() || ElementType
!= T
->getElementType()) {
5796 Result
= getDerived().RebuildConstantMatrixType(
5797 ElementType
, T
->getNumRows(), T
->getNumColumns());
5798 if (Result
.isNull())
5802 ConstantMatrixTypeLoc NewTL
= TLB
.push
<ConstantMatrixTypeLoc
>(Result
);
5803 NewTL
.setAttrNameLoc(TL
.getAttrNameLoc());
5804 NewTL
.setAttrOperandParensRange(TL
.getAttrOperandParensRange());
5805 NewTL
.setAttrRowOperand(TL
.getAttrRowOperand());
5806 NewTL
.setAttrColumnOperand(TL
.getAttrColumnOperand());
5811 template <typename Derived
>
5812 QualType TreeTransform
<Derived
>::TransformDependentSizedMatrixType(
5813 TypeLocBuilder
&TLB
, DependentSizedMatrixTypeLoc TL
) {
5814 const DependentSizedMatrixType
*T
= TL
.getTypePtr();
5816 QualType ElementType
= getDerived().TransformType(T
->getElementType());
5817 if (ElementType
.isNull()) {
5821 // Matrix dimensions are constant expressions.
5822 EnterExpressionEvaluationContext
Unevaluated(
5823 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
5825 Expr
*origRows
= TL
.getAttrRowOperand();
5827 origRows
= T
->getRowExpr();
5828 Expr
*origColumns
= TL
.getAttrColumnOperand();
5830 origColumns
= T
->getColumnExpr();
5832 ExprResult rowResult
= getDerived().TransformExpr(origRows
);
5833 rowResult
= SemaRef
.ActOnConstantExpression(rowResult
);
5834 if (rowResult
.isInvalid())
5837 ExprResult columnResult
= getDerived().TransformExpr(origColumns
);
5838 columnResult
= SemaRef
.ActOnConstantExpression(columnResult
);
5839 if (columnResult
.isInvalid())
5842 Expr
*rows
= rowResult
.get();
5843 Expr
*columns
= columnResult
.get();
5845 QualType Result
= TL
.getType();
5846 if (getDerived().AlwaysRebuild() || ElementType
!= T
->getElementType() ||
5847 rows
!= origRows
|| columns
!= origColumns
) {
5848 Result
= getDerived().RebuildDependentSizedMatrixType(
5849 ElementType
, rows
, columns
, T
->getAttributeLoc());
5851 if (Result
.isNull())
5855 // We might have any sort of matrix type now, but fortunately they
5856 // all have the same location layout.
5857 MatrixTypeLoc NewTL
= TLB
.push
<MatrixTypeLoc
>(Result
);
5858 NewTL
.setAttrNameLoc(TL
.getAttrNameLoc());
5859 NewTL
.setAttrOperandParensRange(TL
.getAttrOperandParensRange());
5860 NewTL
.setAttrRowOperand(rows
);
5861 NewTL
.setAttrColumnOperand(columns
);
5865 template <typename Derived
>
5866 QualType TreeTransform
<Derived
>::TransformDependentAddressSpaceType(
5867 TypeLocBuilder
&TLB
, DependentAddressSpaceTypeLoc TL
) {
5868 const DependentAddressSpaceType
*T
= TL
.getTypePtr();
5870 QualType pointeeType
=
5871 getDerived().TransformType(TLB
, TL
.getPointeeTypeLoc());
5873 if (pointeeType
.isNull())
5876 // Address spaces are constant expressions.
5877 EnterExpressionEvaluationContext
Unevaluated(
5878 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
5880 ExprResult AddrSpace
= getDerived().TransformExpr(T
->getAddrSpaceExpr());
5881 AddrSpace
= SemaRef
.ActOnConstantExpression(AddrSpace
);
5882 if (AddrSpace
.isInvalid())
5885 QualType Result
= TL
.getType();
5886 if (getDerived().AlwaysRebuild() || pointeeType
!= T
->getPointeeType() ||
5887 AddrSpace
.get() != T
->getAddrSpaceExpr()) {
5888 Result
= getDerived().RebuildDependentAddressSpaceType(
5889 pointeeType
, AddrSpace
.get(), T
->getAttributeLoc());
5890 if (Result
.isNull())
5894 // Result might be dependent or not.
5895 if (isa
<DependentAddressSpaceType
>(Result
)) {
5896 DependentAddressSpaceTypeLoc NewTL
=
5897 TLB
.push
<DependentAddressSpaceTypeLoc
>(Result
);
5899 NewTL
.setAttrOperandParensRange(TL
.getAttrOperandParensRange());
5900 NewTL
.setAttrExprOperand(TL
.getAttrExprOperand());
5901 NewTL
.setAttrNameLoc(TL
.getAttrNameLoc());
5904 TLB
.TypeWasModifiedSafely(Result
);
5910 template <typename Derived
>
5911 QualType TreeTransform
<Derived
>::TransformVectorType(TypeLocBuilder
&TLB
,
5913 const VectorType
*T
= TL
.getTypePtr();
5914 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5915 if (ElementType
.isNull())
5918 QualType Result
= TL
.getType();
5919 if (getDerived().AlwaysRebuild() ||
5920 ElementType
!= T
->getElementType()) {
5921 Result
= getDerived().RebuildVectorType(ElementType
, T
->getNumElements(),
5922 T
->getVectorKind());
5923 if (Result
.isNull())
5927 VectorTypeLoc NewTL
= TLB
.push
<VectorTypeLoc
>(Result
);
5928 NewTL
.setNameLoc(TL
.getNameLoc());
5933 template<typename Derived
>
5934 QualType TreeTransform
<Derived
>::TransformExtVectorType(TypeLocBuilder
&TLB
,
5935 ExtVectorTypeLoc TL
) {
5936 const VectorType
*T
= TL
.getTypePtr();
5937 QualType ElementType
= getDerived().TransformType(TLB
, TL
.getElementLoc());
5938 if (ElementType
.isNull())
5941 QualType Result
= TL
.getType();
5942 if (getDerived().AlwaysRebuild() ||
5943 ElementType
!= T
->getElementType()) {
5944 Result
= getDerived().RebuildExtVectorType(ElementType
,
5945 T
->getNumElements(),
5946 /*FIXME*/ SourceLocation());
5947 if (Result
.isNull())
5951 ExtVectorTypeLoc NewTL
= TLB
.push
<ExtVectorTypeLoc
>(Result
);
5952 NewTL
.setNameLoc(TL
.getNameLoc());
5957 template <typename Derived
>
5958 ParmVarDecl
*TreeTransform
<Derived
>::TransformFunctionTypeParam(
5959 ParmVarDecl
*OldParm
, int indexAdjustment
,
5960 std::optional
<unsigned> NumExpansions
, bool ExpectParameterPack
) {
5961 TypeSourceInfo
*OldDI
= OldParm
->getTypeSourceInfo();
5962 TypeSourceInfo
*NewDI
= nullptr;
5964 if (NumExpansions
&& isa
<PackExpansionType
>(OldDI
->getType())) {
5965 // If we're substituting into a pack expansion type and we know the
5966 // length we want to expand to, just substitute for the pattern.
5967 TypeLoc OldTL
= OldDI
->getTypeLoc();
5968 PackExpansionTypeLoc OldExpansionTL
= OldTL
.castAs
<PackExpansionTypeLoc
>();
5971 TypeLoc NewTL
= OldDI
->getTypeLoc();
5972 TLB
.reserve(NewTL
.getFullDataSize());
5974 QualType Result
= getDerived().TransformType(TLB
,
5975 OldExpansionTL
.getPatternLoc());
5976 if (Result
.isNull())
5979 Result
= RebuildPackExpansionType(Result
,
5980 OldExpansionTL
.getPatternLoc().getSourceRange(),
5981 OldExpansionTL
.getEllipsisLoc(),
5983 if (Result
.isNull())
5986 PackExpansionTypeLoc NewExpansionTL
5987 = TLB
.push
<PackExpansionTypeLoc
>(Result
);
5988 NewExpansionTL
.setEllipsisLoc(OldExpansionTL
.getEllipsisLoc());
5989 NewDI
= TLB
.getTypeSourceInfo(SemaRef
.Context
, Result
);
5991 NewDI
= getDerived().TransformType(OldDI
);
5995 if (NewDI
== OldDI
&& indexAdjustment
== 0)
5998 ParmVarDecl
*newParm
= ParmVarDecl::Create(SemaRef
.Context
,
5999 OldParm
->getDeclContext(),
6000 OldParm
->getInnerLocStart(),
6001 OldParm
->getLocation(),
6002 OldParm
->getIdentifier(),
6005 OldParm
->getStorageClass(),
6006 /* DefArg */ nullptr);
6007 newParm
->setScopeInfo(OldParm
->getFunctionScopeDepth(),
6008 OldParm
->getFunctionScopeIndex() + indexAdjustment
);
6009 transformedLocalDecl(OldParm
, {newParm
});
6013 template <typename Derived
>
6014 bool TreeTransform
<Derived
>::TransformFunctionTypeParams(
6015 SourceLocation Loc
, ArrayRef
<ParmVarDecl
*> Params
,
6016 const QualType
*ParamTypes
,
6017 const FunctionProtoType::ExtParameterInfo
*ParamInfos
,
6018 SmallVectorImpl
<QualType
> &OutParamTypes
,
6019 SmallVectorImpl
<ParmVarDecl
*> *PVars
,
6020 Sema::ExtParameterInfoBuilder
&PInfos
,
6021 unsigned *LastParamTransformed
) {
6022 int indexAdjustment
= 0;
6024 unsigned NumParams
= Params
.size();
6025 for (unsigned i
= 0; i
!= NumParams
; ++i
) {
6026 if (LastParamTransformed
)
6027 *LastParamTransformed
= i
;
6028 if (ParmVarDecl
*OldParm
= Params
[i
]) {
6029 assert(OldParm
->getFunctionScopeIndex() == i
);
6031 std::optional
<unsigned> NumExpansions
;
6032 ParmVarDecl
*NewParm
= nullptr;
6033 if (OldParm
->isParameterPack()) {
6034 // We have a function parameter pack that may need to be expanded.
6035 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
6037 // Find the parameter packs that could be expanded.
6038 TypeLoc TL
= OldParm
->getTypeSourceInfo()->getTypeLoc();
6039 PackExpansionTypeLoc ExpansionTL
= TL
.castAs
<PackExpansionTypeLoc
>();
6040 TypeLoc Pattern
= ExpansionTL
.getPatternLoc();
6041 SemaRef
.collectUnexpandedParameterPacks(Pattern
, Unexpanded
);
6043 // Determine whether we should expand the parameter packs.
6044 bool ShouldExpand
= false;
6045 bool RetainExpansion
= false;
6046 std::optional
<unsigned> OrigNumExpansions
;
6047 if (Unexpanded
.size() > 0) {
6048 OrigNumExpansions
= ExpansionTL
.getTypePtr()->getNumExpansions();
6049 NumExpansions
= OrigNumExpansions
;
6050 if (getDerived().TryExpandParameterPacks(ExpansionTL
.getEllipsisLoc(),
6051 Pattern
.getSourceRange(),
6060 const AutoType
*AT
=
6061 Pattern
.getType().getTypePtr()->getContainedAutoType();
6062 assert((AT
&& (!AT
->isDeduced() || AT
->getDeducedType().isNull())) &&
6063 "Could not find parameter packs or undeduced auto type!");
6068 // Expand the function parameter pack into multiple, separate
6070 getDerived().ExpandingFunctionParameterPack(OldParm
);
6071 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
6072 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
6073 ParmVarDecl
*NewParm
6074 = getDerived().TransformFunctionTypeParam(OldParm
,
6077 /*ExpectParameterPack=*/false);
6082 PInfos
.set(OutParamTypes
.size(), ParamInfos
[i
]);
6083 OutParamTypes
.push_back(NewParm
->getType());
6085 PVars
->push_back(NewParm
);
6088 // If we're supposed to retain a pack expansion, do so by temporarily
6089 // forgetting the partially-substituted parameter pack.
6090 if (RetainExpansion
) {
6091 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
6092 ParmVarDecl
*NewParm
6093 = getDerived().TransformFunctionTypeParam(OldParm
,
6096 /*ExpectParameterPack=*/false);
6101 PInfos
.set(OutParamTypes
.size(), ParamInfos
[i
]);
6102 OutParamTypes
.push_back(NewParm
->getType());
6104 PVars
->push_back(NewParm
);
6107 // The next parameter should have the same adjustment as the
6108 // last thing we pushed, but we post-incremented indexAdjustment
6109 // on every push. Also, if we push nothing, the adjustment should
6113 // We're done with the pack expansion.
6117 // We'll substitute the parameter now without expanding the pack
6119 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
6120 NewParm
= getDerived().TransformFunctionTypeParam(OldParm
,
6123 /*ExpectParameterPack=*/true);
6124 assert(NewParm
->isParameterPack() &&
6125 "Parameter pack no longer a parameter pack after "
6128 NewParm
= getDerived().TransformFunctionTypeParam(
6129 OldParm
, indexAdjustment
, std::nullopt
,
6130 /*ExpectParameterPack=*/false);
6137 PInfos
.set(OutParamTypes
.size(), ParamInfos
[i
]);
6138 OutParamTypes
.push_back(NewParm
->getType());
6140 PVars
->push_back(NewParm
);
6144 // Deal with the possibility that we don't have a parameter
6145 // declaration for this parameter.
6147 QualType OldType
= ParamTypes
[i
];
6148 bool IsPackExpansion
= false;
6149 std::optional
<unsigned> NumExpansions
;
6151 if (const PackExpansionType
*Expansion
6152 = dyn_cast
<PackExpansionType
>(OldType
)) {
6153 // We have a function parameter pack that may need to be expanded.
6154 QualType Pattern
= Expansion
->getPattern();
6155 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
6156 getSema().collectUnexpandedParameterPacks(Pattern
, Unexpanded
);
6158 // Determine whether we should expand the parameter packs.
6159 bool ShouldExpand
= false;
6160 bool RetainExpansion
= false;
6161 if (getDerived().TryExpandParameterPacks(Loc
, SourceRange(),
6170 // Expand the function parameter pack into multiple, separate
6172 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
6173 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
6174 QualType NewType
= getDerived().TransformType(Pattern
);
6175 if (NewType
.isNull())
6178 if (NewType
->containsUnexpandedParameterPack()) {
6179 NewType
= getSema().getASTContext().getPackExpansionType(
6180 NewType
, std::nullopt
);
6182 if (NewType
.isNull())
6187 PInfos
.set(OutParamTypes
.size(), ParamInfos
[i
]);
6188 OutParamTypes
.push_back(NewType
);
6190 PVars
->push_back(nullptr);
6193 // We're done with the pack expansion.
6197 // If we're supposed to retain a pack expansion, do so by temporarily
6198 // forgetting the partially-substituted parameter pack.
6199 if (RetainExpansion
) {
6200 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
6201 QualType NewType
= getDerived().TransformType(Pattern
);
6202 if (NewType
.isNull())
6206 PInfos
.set(OutParamTypes
.size(), ParamInfos
[i
]);
6207 OutParamTypes
.push_back(NewType
);
6209 PVars
->push_back(nullptr);
6212 // We'll substitute the parameter now without expanding the pack
6214 OldType
= Expansion
->getPattern();
6215 IsPackExpansion
= true;
6216 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
6217 NewType
= getDerived().TransformType(OldType
);
6219 NewType
= getDerived().TransformType(OldType
);
6222 if (NewType
.isNull())
6225 if (IsPackExpansion
)
6226 NewType
= getSema().Context
.getPackExpansionType(NewType
,
6230 PInfos
.set(OutParamTypes
.size(), ParamInfos
[i
]);
6231 OutParamTypes
.push_back(NewType
);
6233 PVars
->push_back(nullptr);
6238 for (unsigned i
= 0, e
= PVars
->size(); i
!= e
; ++i
)
6239 if (ParmVarDecl
*parm
= (*PVars
)[i
])
6240 assert(parm
->getFunctionScopeIndex() == i
);
6247 template<typename Derived
>
6249 TreeTransform
<Derived
>::TransformFunctionProtoType(TypeLocBuilder
&TLB
,
6250 FunctionProtoTypeLoc TL
) {
6251 SmallVector
<QualType
, 4> ExceptionStorage
;
6252 return getDerived().TransformFunctionProtoType(
6253 TLB
, TL
, nullptr, Qualifiers(),
6254 [&](FunctionProtoType::ExceptionSpecInfo
&ESI
, bool &Changed
) {
6255 return getDerived().TransformExceptionSpec(TL
.getBeginLoc(), ESI
,
6256 ExceptionStorage
, Changed
);
6260 template<typename Derived
> template<typename Fn
>
6261 QualType TreeTransform
<Derived
>::TransformFunctionProtoType(
6262 TypeLocBuilder
&TLB
, FunctionProtoTypeLoc TL
, CXXRecordDecl
*ThisContext
,
6263 Qualifiers ThisTypeQuals
, Fn TransformExceptionSpec
) {
6265 // Transform the parameters and return type.
6267 // We are required to instantiate the params and return type in source order.
6268 // When the function has a trailing return type, we instantiate the
6269 // parameters before the return type, since the return type can then refer
6270 // to the parameters themselves (via decltype, sizeof, etc.).
6272 SmallVector
<QualType
, 4> ParamTypes
;
6273 SmallVector
<ParmVarDecl
*, 4> ParamDecls
;
6274 Sema::ExtParameterInfoBuilder ExtParamInfos
;
6275 const FunctionProtoType
*T
= TL
.getTypePtr();
6277 QualType ResultType
;
6279 if (T
->hasTrailingReturn()) {
6280 if (getDerived().TransformFunctionTypeParams(
6281 TL
.getBeginLoc(), TL
.getParams(),
6282 TL
.getTypePtr()->param_type_begin(),
6283 T
->getExtParameterInfosOrNull(),
6284 ParamTypes
, &ParamDecls
, ExtParamInfos
))
6288 // C++11 [expr.prim.general]p3:
6289 // If a declaration declares a member function or member function
6290 // template of a class X, the expression this is a prvalue of type
6291 // "pointer to cv-qualifier-seq X" between the optional cv-qualifer-seq
6292 // and the end of the function-definition, member-declarator, or
6294 auto *RD
= dyn_cast
<CXXRecordDecl
>(SemaRef
.getCurLexicalContext());
6295 Sema::CXXThisScopeRAII
ThisScope(
6296 SemaRef
, !ThisContext
&& RD
? RD
: ThisContext
, ThisTypeQuals
);
6298 ResultType
= getDerived().TransformType(TLB
, TL
.getReturnLoc());
6299 if (ResultType
.isNull())
6304 ResultType
= getDerived().TransformType(TLB
, TL
.getReturnLoc());
6305 if (ResultType
.isNull())
6308 if (getDerived().TransformFunctionTypeParams(
6309 TL
.getBeginLoc(), TL
.getParams(),
6310 TL
.getTypePtr()->param_type_begin(),
6311 T
->getExtParameterInfosOrNull(),
6312 ParamTypes
, &ParamDecls
, ExtParamInfos
))
6316 FunctionProtoType::ExtProtoInfo EPI
= T
->getExtProtoInfo();
6318 bool EPIChanged
= false;
6319 if (TransformExceptionSpec(EPI
.ExceptionSpec
, EPIChanged
))
6322 // Handle extended parameter information.
6323 if (auto NewExtParamInfos
=
6324 ExtParamInfos
.getPointerOrNull(ParamTypes
.size())) {
6325 if (!EPI
.ExtParameterInfos
||
6326 llvm::ArrayRef(EPI
.ExtParameterInfos
, TL
.getNumParams()) !=
6327 llvm::ArrayRef(NewExtParamInfos
, ParamTypes
.size())) {
6330 EPI
.ExtParameterInfos
= NewExtParamInfos
;
6331 } else if (EPI
.ExtParameterInfos
) {
6333 EPI
.ExtParameterInfos
= nullptr;
6336 // Transform any function effects with unevaluated conditions.
6337 // Hold this set in a local for the rest of this function, since EPI
6338 // may need to hold a FunctionEffectsRef pointing into it.
6339 std::optional
<FunctionEffectSet
> NewFX
;
6340 if (ArrayRef FXConds
= EPI
.FunctionEffects
.conditions(); !FXConds
.empty()) {
6342 EnterExpressionEvaluationContext
Unevaluated(
6343 getSema(), Sema::ExpressionEvaluationContext::ConstantEvaluated
);
6345 for (const FunctionEffectWithCondition
&PrevEC
: EPI
.FunctionEffects
) {
6346 FunctionEffectWithCondition NewEC
= PrevEC
;
6347 if (Expr
*CondExpr
= PrevEC
.Cond
.getCondition()) {
6348 ExprResult NewExpr
= getDerived().TransformExpr(CondExpr
);
6349 if (NewExpr
.isInvalid())
6351 std::optional
<FunctionEffectMode
> Mode
=
6352 SemaRef
.ActOnEffectExpression(NewExpr
.get(), PrevEC
.Effect
.name());
6356 // The condition expression has been transformed, and re-evaluated.
6357 // It may or may not have become constant.
6359 case FunctionEffectMode::True
:
6362 case FunctionEffectMode::False
:
6363 NewEC
.Effect
= FunctionEffect(PrevEC
.Effect
.oppositeKind());
6366 case FunctionEffectMode::Dependent
:
6367 NewEC
.Cond
= EffectConditionExpr(NewExpr
.get());
6369 case FunctionEffectMode::None
:
6371 "FunctionEffectMode::None shouldn't be possible here");
6374 if (!SemaRef
.diagnoseConflictingFunctionEffect(*NewFX
, NewEC
,
6375 TL
.getBeginLoc())) {
6376 FunctionEffectSet::Conflicts Errs
;
6377 NewFX
->insert(NewEC
, Errs
);
6378 assert(Errs
.empty());
6381 EPI
.FunctionEffects
= *NewFX
;
6385 QualType Result
= TL
.getType();
6386 if (getDerived().AlwaysRebuild() || ResultType
!= T
->getReturnType() ||
6387 T
->getParamTypes() != llvm::ArrayRef(ParamTypes
) || EPIChanged
) {
6388 Result
= getDerived().RebuildFunctionProtoType(ResultType
, ParamTypes
, EPI
);
6389 if (Result
.isNull())
6393 FunctionProtoTypeLoc NewTL
= TLB
.push
<FunctionProtoTypeLoc
>(Result
);
6394 NewTL
.setLocalRangeBegin(TL
.getLocalRangeBegin());
6395 NewTL
.setLParenLoc(TL
.getLParenLoc());
6396 NewTL
.setRParenLoc(TL
.getRParenLoc());
6397 NewTL
.setExceptionSpecRange(TL
.getExceptionSpecRange());
6398 NewTL
.setLocalRangeEnd(TL
.getLocalRangeEnd());
6399 for (unsigned i
= 0, e
= NewTL
.getNumParams(); i
!= e
; ++i
)
6400 NewTL
.setParam(i
, ParamDecls
[i
]);
6405 template<typename Derived
>
6406 bool TreeTransform
<Derived
>::TransformExceptionSpec(
6407 SourceLocation Loc
, FunctionProtoType::ExceptionSpecInfo
&ESI
,
6408 SmallVectorImpl
<QualType
> &Exceptions
, bool &Changed
) {
6409 assert(ESI
.Type
!= EST_Uninstantiated
&& ESI
.Type
!= EST_Unevaluated
);
6411 // Instantiate a dynamic noexcept expression, if any.
6412 if (isComputedNoexcept(ESI
.Type
)) {
6413 // Update this scrope because ContextDecl in Sema will be used in
6415 auto *Method
= dyn_cast_if_present
<CXXMethodDecl
>(ESI
.SourceTemplate
);
6416 Sema::CXXThisScopeRAII
ThisScope(
6417 SemaRef
, Method
? Method
->getParent() : nullptr,
6418 Method
? Method
->getMethodQualifiers() : Qualifiers
{},
6420 EnterExpressionEvaluationContext
Unevaluated(
6421 getSema(), Sema::ExpressionEvaluationContext::ConstantEvaluated
);
6422 ExprResult NoexceptExpr
= getDerived().TransformExpr(ESI
.NoexceptExpr
);
6423 if (NoexceptExpr
.isInvalid())
6426 ExceptionSpecificationType EST
= ESI
.Type
;
6428 getSema().ActOnNoexceptSpec(NoexceptExpr
.get(), EST
);
6429 if (NoexceptExpr
.isInvalid())
6432 if (ESI
.NoexceptExpr
!= NoexceptExpr
.get() || EST
!= ESI
.Type
)
6434 ESI
.NoexceptExpr
= NoexceptExpr
.get();
6438 if (ESI
.Type
!= EST_Dynamic
)
6441 // Instantiate a dynamic exception specification's type.
6442 for (QualType T
: ESI
.Exceptions
) {
6443 if (const PackExpansionType
*PackExpansion
=
6444 T
->getAs
<PackExpansionType
>()) {
6447 // We have a pack expansion. Instantiate it.
6448 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
6449 SemaRef
.collectUnexpandedParameterPacks(PackExpansion
->getPattern(),
6451 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
6453 // Determine whether the set of unexpanded parameter packs can and
6456 bool Expand
= false;
6457 bool RetainExpansion
= false;
6458 std::optional
<unsigned> NumExpansions
= PackExpansion
->getNumExpansions();
6459 // FIXME: Track the location of the ellipsis (and track source location
6460 // information for the types in the exception specification in general).
6461 if (getDerived().TryExpandParameterPacks(
6462 Loc
, SourceRange(), Unexpanded
, Expand
,
6463 RetainExpansion
, NumExpansions
))
6467 // We can't expand this pack expansion into separate arguments yet;
6468 // just substitute into the pattern and create a new pack expansion
6470 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
6471 QualType U
= getDerived().TransformType(PackExpansion
->getPattern());
6475 U
= SemaRef
.Context
.getPackExpansionType(U
, NumExpansions
);
6476 Exceptions
.push_back(U
);
6480 // Substitute into the pack expansion pattern for each slice of the
6482 for (unsigned ArgIdx
= 0; ArgIdx
!= *NumExpansions
; ++ArgIdx
) {
6483 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), ArgIdx
);
6485 QualType U
= getDerived().TransformType(PackExpansion
->getPattern());
6486 if (U
.isNull() || SemaRef
.CheckSpecifiedExceptionType(U
, Loc
))
6489 Exceptions
.push_back(U
);
6492 QualType U
= getDerived().TransformType(T
);
6493 if (U
.isNull() || SemaRef
.CheckSpecifiedExceptionType(U
, Loc
))
6498 Exceptions
.push_back(U
);
6502 ESI
.Exceptions
= Exceptions
;
6503 if (ESI
.Exceptions
.empty())
6504 ESI
.Type
= EST_DynamicNone
;
6508 template<typename Derived
>
6509 QualType TreeTransform
<Derived
>::TransformFunctionNoProtoType(
6510 TypeLocBuilder
&TLB
,
6511 FunctionNoProtoTypeLoc TL
) {
6512 const FunctionNoProtoType
*T
= TL
.getTypePtr();
6513 QualType ResultType
= getDerived().TransformType(TLB
, TL
.getReturnLoc());
6514 if (ResultType
.isNull())
6517 QualType Result
= TL
.getType();
6518 if (getDerived().AlwaysRebuild() || ResultType
!= T
->getReturnType())
6519 Result
= getDerived().RebuildFunctionNoProtoType(ResultType
);
6521 FunctionNoProtoTypeLoc NewTL
= TLB
.push
<FunctionNoProtoTypeLoc
>(Result
);
6522 NewTL
.setLocalRangeBegin(TL
.getLocalRangeBegin());
6523 NewTL
.setLParenLoc(TL
.getLParenLoc());
6524 NewTL
.setRParenLoc(TL
.getRParenLoc());
6525 NewTL
.setLocalRangeEnd(TL
.getLocalRangeEnd());
6530 template <typename Derived
>
6531 QualType TreeTransform
<Derived
>::TransformUnresolvedUsingType(
6532 TypeLocBuilder
&TLB
, UnresolvedUsingTypeLoc TL
) {
6533 const UnresolvedUsingType
*T
= TL
.getTypePtr();
6534 Decl
*D
= getDerived().TransformDecl(TL
.getNameLoc(), T
->getDecl());
6538 QualType Result
= TL
.getType();
6539 if (getDerived().AlwaysRebuild() || D
!= T
->getDecl()) {
6540 Result
= getDerived().RebuildUnresolvedUsingType(TL
.getNameLoc(), D
);
6541 if (Result
.isNull())
6545 // We might get an arbitrary type spec type back. We should at
6546 // least always get a type spec type, though.
6547 TypeSpecTypeLoc NewTL
= TLB
.pushTypeSpec(Result
);
6548 NewTL
.setNameLoc(TL
.getNameLoc());
6553 template <typename Derived
>
6554 QualType TreeTransform
<Derived
>::TransformUsingType(TypeLocBuilder
&TLB
,
6556 const UsingType
*T
= TL
.getTypePtr();
6558 auto *Found
= cast_or_null
<UsingShadowDecl
>(getDerived().TransformDecl(
6559 TL
.getLocalSourceRange().getBegin(), T
->getFoundDecl()));
6563 QualType Underlying
= getDerived().TransformType(T
->desugar());
6564 if (Underlying
.isNull())
6567 QualType Result
= TL
.getType();
6568 if (getDerived().AlwaysRebuild() || Found
!= T
->getFoundDecl() ||
6569 Underlying
!= T
->getUnderlyingType()) {
6570 Result
= getDerived().RebuildUsingType(Found
, Underlying
);
6571 if (Result
.isNull())
6575 TLB
.pushTypeSpec(Result
).setNameLoc(TL
.getNameLoc());
6579 template<typename Derived
>
6580 QualType TreeTransform
<Derived
>::TransformTypedefType(TypeLocBuilder
&TLB
,
6581 TypedefTypeLoc TL
) {
6582 const TypedefType
*T
= TL
.getTypePtr();
6583 TypedefNameDecl
*Typedef
6584 = cast_or_null
<TypedefNameDecl
>(getDerived().TransformDecl(TL
.getNameLoc(),
6589 QualType Result
= TL
.getType();
6590 if (getDerived().AlwaysRebuild() ||
6591 Typedef
!= T
->getDecl()) {
6592 Result
= getDerived().RebuildTypedefType(Typedef
);
6593 if (Result
.isNull())
6597 TypedefTypeLoc NewTL
= TLB
.push
<TypedefTypeLoc
>(Result
);
6598 NewTL
.setNameLoc(TL
.getNameLoc());
6603 template<typename Derived
>
6604 QualType TreeTransform
<Derived
>::TransformTypeOfExprType(TypeLocBuilder
&TLB
,
6605 TypeOfExprTypeLoc TL
) {
6606 // typeof expressions are not potentially evaluated contexts
6607 EnterExpressionEvaluationContext
Unevaluated(
6608 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
,
6609 Sema::ReuseLambdaContextDecl
);
6611 ExprResult E
= getDerived().TransformExpr(TL
.getUnderlyingExpr());
6615 E
= SemaRef
.HandleExprEvaluationContextForTypeof(E
.get());
6619 QualType Result
= TL
.getType();
6620 TypeOfKind Kind
= Result
->castAs
<TypeOfExprType
>()->getKind();
6621 if (getDerived().AlwaysRebuild() || E
.get() != TL
.getUnderlyingExpr()) {
6623 getDerived().RebuildTypeOfExprType(E
.get(), TL
.getTypeofLoc(), Kind
);
6624 if (Result
.isNull())
6628 TypeOfExprTypeLoc NewTL
= TLB
.push
<TypeOfExprTypeLoc
>(Result
);
6629 NewTL
.setTypeofLoc(TL
.getTypeofLoc());
6630 NewTL
.setLParenLoc(TL
.getLParenLoc());
6631 NewTL
.setRParenLoc(TL
.getRParenLoc());
6636 template<typename Derived
>
6637 QualType TreeTransform
<Derived
>::TransformTypeOfType(TypeLocBuilder
&TLB
,
6639 TypeSourceInfo
* Old_Under_TI
= TL
.getUnmodifiedTInfo();
6640 TypeSourceInfo
* New_Under_TI
= getDerived().TransformType(Old_Under_TI
);
6644 QualType Result
= TL
.getType();
6645 TypeOfKind Kind
= Result
->castAs
<TypeOfType
>()->getKind();
6646 if (getDerived().AlwaysRebuild() || New_Under_TI
!= Old_Under_TI
) {
6647 Result
= getDerived().RebuildTypeOfType(New_Under_TI
->getType(), Kind
);
6648 if (Result
.isNull())
6652 TypeOfTypeLoc NewTL
= TLB
.push
<TypeOfTypeLoc
>(Result
);
6653 NewTL
.setTypeofLoc(TL
.getTypeofLoc());
6654 NewTL
.setLParenLoc(TL
.getLParenLoc());
6655 NewTL
.setRParenLoc(TL
.getRParenLoc());
6656 NewTL
.setUnmodifiedTInfo(New_Under_TI
);
6661 template<typename Derived
>
6662 QualType TreeTransform
<Derived
>::TransformDecltypeType(TypeLocBuilder
&TLB
,
6663 DecltypeTypeLoc TL
) {
6664 const DecltypeType
*T
= TL
.getTypePtr();
6666 // decltype expressions are not potentially evaluated contexts
6667 EnterExpressionEvaluationContext
Unevaluated(
6668 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
, nullptr,
6669 Sema::ExpressionEvaluationContextRecord::EK_Decltype
);
6671 ExprResult E
= getDerived().TransformExpr(T
->getUnderlyingExpr());
6675 E
= getSema().ActOnDecltypeExpression(E
.get());
6679 QualType Result
= TL
.getType();
6680 if (getDerived().AlwaysRebuild() ||
6681 E
.get() != T
->getUnderlyingExpr()) {
6682 Result
= getDerived().RebuildDecltypeType(E
.get(), TL
.getDecltypeLoc());
6683 if (Result
.isNull())
6688 DecltypeTypeLoc NewTL
= TLB
.push
<DecltypeTypeLoc
>(Result
);
6689 NewTL
.setDecltypeLoc(TL
.getDecltypeLoc());
6690 NewTL
.setRParenLoc(TL
.getRParenLoc());
6694 template <typename Derived
>
6696 TreeTransform
<Derived
>::TransformPackIndexingType(TypeLocBuilder
&TLB
,
6697 PackIndexingTypeLoc TL
) {
6698 // Transform the index
6699 ExprResult IndexExpr
;
6701 EnterExpressionEvaluationContext
ConstantContext(
6702 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
6704 IndexExpr
= getDerived().TransformExpr(TL
.getIndexExpr());
6705 if (IndexExpr
.isInvalid())
6708 QualType Pattern
= TL
.getPattern();
6710 const PackIndexingType
*PIT
= TL
.getTypePtr();
6711 SmallVector
<QualType
, 5> SubtitutedTypes
;
6712 llvm::ArrayRef
<QualType
> Types
= PIT
->getExpansions();
6714 bool NotYetExpanded
= Types
.empty();
6715 bool FullySubstituted
= true;
6717 if (Types
.empty() && !PIT
->expandsToEmptyPack())
6718 Types
= llvm::ArrayRef
<QualType
>(&Pattern
, 1);
6720 for (QualType T
: Types
) {
6721 if (!T
->containsUnexpandedParameterPack()) {
6722 QualType Transformed
= getDerived().TransformType(T
);
6723 if (Transformed
.isNull())
6725 SubtitutedTypes
.push_back(Transformed
);
6729 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
6730 getSema().collectUnexpandedParameterPacks(T
, Unexpanded
);
6731 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
6732 // Determine whether the set of unexpanded parameter packs can and should
6734 bool ShouldExpand
= true;
6735 bool RetainExpansion
= false;
6736 std::optional
<unsigned> OrigNumExpansions
;
6737 std::optional
<unsigned> NumExpansions
= OrigNumExpansions
;
6738 if (getDerived().TryExpandParameterPacks(TL
.getEllipsisLoc(), SourceRange(),
6739 Unexpanded
, ShouldExpand
,
6740 RetainExpansion
, NumExpansions
))
6742 if (!ShouldExpand
) {
6743 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
6744 // FIXME: should we keep TypeLoc for individual expansions in
6745 // PackIndexingTypeLoc?
6746 TypeSourceInfo
*TI
=
6747 SemaRef
.getASTContext().getTrivialTypeSourceInfo(T
, TL
.getBeginLoc());
6748 QualType Pack
= getDerived().TransformType(TLB
, TI
->getTypeLoc());
6751 if (NotYetExpanded
) {
6752 FullySubstituted
= false;
6753 QualType Out
= getDerived().RebuildPackIndexingType(
6754 Pack
, IndexExpr
.get(), SourceLocation(), TL
.getEllipsisLoc(),
6759 PackIndexingTypeLoc Loc
= TLB
.push
<PackIndexingTypeLoc
>(Out
);
6760 Loc
.setEllipsisLoc(TL
.getEllipsisLoc());
6763 SubtitutedTypes
.push_back(Pack
);
6766 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
6767 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
6768 QualType Out
= getDerived().TransformType(T
);
6771 SubtitutedTypes
.push_back(Out
);
6772 FullySubstituted
&= !Out
->containsUnexpandedParameterPack();
6774 // If we're supposed to retain a pack expansion, do so by temporarily
6775 // forgetting the partially-substituted parameter pack.
6776 if (RetainExpansion
) {
6777 FullySubstituted
= false;
6778 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
6779 QualType Out
= getDerived().TransformType(T
);
6782 SubtitutedTypes
.push_back(Out
);
6786 // A pack indexing type can appear in a larger pack expansion,
6787 // e.g. `Pack...[pack_of_indexes]...`
6788 // so we need to temporarily disable substitution of pack elements
6789 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
6790 QualType Result
= getDerived().TransformType(TLB
, TL
.getPatternLoc());
6792 QualType Out
= getDerived().RebuildPackIndexingType(
6793 Result
, IndexExpr
.get(), SourceLocation(), TL
.getEllipsisLoc(),
6794 FullySubstituted
, SubtitutedTypes
);
6798 PackIndexingTypeLoc Loc
= TLB
.push
<PackIndexingTypeLoc
>(Out
);
6799 Loc
.setEllipsisLoc(TL
.getEllipsisLoc());
6803 template<typename Derived
>
6804 QualType TreeTransform
<Derived
>::TransformUnaryTransformType(
6805 TypeLocBuilder
&TLB
,
6806 UnaryTransformTypeLoc TL
) {
6807 QualType Result
= TL
.getType();
6808 if (Result
->isDependentType()) {
6809 const UnaryTransformType
*T
= TL
.getTypePtr();
6811 TypeSourceInfo
*NewBaseTSI
=
6812 getDerived().TransformType(TL
.getUnderlyingTInfo());
6815 QualType NewBase
= NewBaseTSI
->getType();
6817 Result
= getDerived().RebuildUnaryTransformType(NewBase
,
6820 if (Result
.isNull())
6824 UnaryTransformTypeLoc NewTL
= TLB
.push
<UnaryTransformTypeLoc
>(Result
);
6825 NewTL
.setKWLoc(TL
.getKWLoc());
6826 NewTL
.setParensRange(TL
.getParensRange());
6827 NewTL
.setUnderlyingTInfo(TL
.getUnderlyingTInfo());
6831 template<typename Derived
>
6832 QualType TreeTransform
<Derived
>::TransformDeducedTemplateSpecializationType(
6833 TypeLocBuilder
&TLB
, DeducedTemplateSpecializationTypeLoc TL
) {
6834 const DeducedTemplateSpecializationType
*T
= TL
.getTypePtr();
6837 TemplateName TemplateName
= getDerived().TransformTemplateName(
6838 SS
, T
->getTemplateName(), TL
.getTemplateNameLoc());
6839 if (TemplateName
.isNull())
6842 QualType OldDeduced
= T
->getDeducedType();
6843 QualType NewDeduced
;
6844 if (!OldDeduced
.isNull()) {
6845 NewDeduced
= getDerived().TransformType(OldDeduced
);
6846 if (NewDeduced
.isNull())
6850 QualType Result
= getDerived().RebuildDeducedTemplateSpecializationType(
6851 TemplateName
, NewDeduced
);
6852 if (Result
.isNull())
6855 DeducedTemplateSpecializationTypeLoc NewTL
=
6856 TLB
.push
<DeducedTemplateSpecializationTypeLoc
>(Result
);
6857 NewTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
6862 template<typename Derived
>
6863 QualType TreeTransform
<Derived
>::TransformRecordType(TypeLocBuilder
&TLB
,
6865 const RecordType
*T
= TL
.getTypePtr();
6867 = cast_or_null
<RecordDecl
>(getDerived().TransformDecl(TL
.getNameLoc(),
6872 QualType Result
= TL
.getType();
6873 if (getDerived().AlwaysRebuild() ||
6874 Record
!= T
->getDecl()) {
6875 Result
= getDerived().RebuildRecordType(Record
);
6876 if (Result
.isNull())
6880 RecordTypeLoc NewTL
= TLB
.push
<RecordTypeLoc
>(Result
);
6881 NewTL
.setNameLoc(TL
.getNameLoc());
6886 template<typename Derived
>
6887 QualType TreeTransform
<Derived
>::TransformEnumType(TypeLocBuilder
&TLB
,
6889 const EnumType
*T
= TL
.getTypePtr();
6891 = cast_or_null
<EnumDecl
>(getDerived().TransformDecl(TL
.getNameLoc(),
6896 QualType Result
= TL
.getType();
6897 if (getDerived().AlwaysRebuild() ||
6898 Enum
!= T
->getDecl()) {
6899 Result
= getDerived().RebuildEnumType(Enum
);
6900 if (Result
.isNull())
6904 EnumTypeLoc NewTL
= TLB
.push
<EnumTypeLoc
>(Result
);
6905 NewTL
.setNameLoc(TL
.getNameLoc());
6910 template<typename Derived
>
6911 QualType TreeTransform
<Derived
>::TransformInjectedClassNameType(
6912 TypeLocBuilder
&TLB
,
6913 InjectedClassNameTypeLoc TL
) {
6914 Decl
*D
= getDerived().TransformDecl(TL
.getNameLoc(),
6915 TL
.getTypePtr()->getDecl());
6916 if (!D
) return QualType();
6918 QualType T
= SemaRef
.Context
.getTypeDeclType(cast
<TypeDecl
>(D
));
6919 TLB
.pushTypeSpec(T
).setNameLoc(TL
.getNameLoc());
6923 template<typename Derived
>
6924 QualType TreeTransform
<Derived
>::TransformTemplateTypeParmType(
6925 TypeLocBuilder
&TLB
,
6926 TemplateTypeParmTypeLoc TL
) {
6927 return getDerived().TransformTemplateTypeParmType(
6929 /*SuppressObjCLifetime=*/false);
6932 template <typename Derived
>
6933 QualType TreeTransform
<Derived
>::TransformTemplateTypeParmType(
6934 TypeLocBuilder
&TLB
, TemplateTypeParmTypeLoc TL
, bool) {
6935 return TransformTypeSpecType(TLB
, TL
);
6938 template<typename Derived
>
6939 QualType TreeTransform
<Derived
>::TransformSubstTemplateTypeParmType(
6940 TypeLocBuilder
&TLB
,
6941 SubstTemplateTypeParmTypeLoc TL
) {
6942 const SubstTemplateTypeParmType
*T
= TL
.getTypePtr();
6945 getDerived().TransformDecl(TL
.getNameLoc(), T
->getAssociatedDecl());
6947 // Substitute into the replacement type, which itself might involve something
6948 // that needs to be transformed. This only tends to occur with default
6949 // template arguments of template template parameters.
6950 TemporaryBase
Rebase(*this, TL
.getNameLoc(), DeclarationName());
6951 QualType Replacement
= getDerived().TransformType(T
->getReplacementType());
6952 if (Replacement
.isNull())
6955 QualType Result
= SemaRef
.Context
.getSubstTemplateTypeParmType(
6956 Replacement
, NewReplaced
, T
->getIndex(), T
->getPackIndex());
6958 // Propagate type-source information.
6959 SubstTemplateTypeParmTypeLoc NewTL
6960 = TLB
.push
<SubstTemplateTypeParmTypeLoc
>(Result
);
6961 NewTL
.setNameLoc(TL
.getNameLoc());
6966 template<typename Derived
>
6967 QualType TreeTransform
<Derived
>::TransformSubstTemplateTypeParmPackType(
6968 TypeLocBuilder
&TLB
,
6969 SubstTemplateTypeParmPackTypeLoc TL
) {
6970 return getDerived().TransformSubstTemplateTypeParmPackType(
6971 TLB
, TL
, /*SuppressObjCLifetime=*/false);
6974 template <typename Derived
>
6975 QualType TreeTransform
<Derived
>::TransformSubstTemplateTypeParmPackType(
6976 TypeLocBuilder
&TLB
, SubstTemplateTypeParmPackTypeLoc TL
, bool) {
6977 return TransformTypeSpecType(TLB
, TL
);
6980 template<typename Derived
>
6981 QualType TreeTransform
<Derived
>::TransformTemplateSpecializationType(
6982 TypeLocBuilder
&TLB
,
6983 TemplateSpecializationTypeLoc TL
) {
6984 const TemplateSpecializationType
*T
= TL
.getTypePtr();
6986 // The nested-name-specifier never matters in a TemplateSpecializationType,
6987 // because we can't have a dependent nested-name-specifier anyway.
6989 TemplateName Template
6990 = getDerived().TransformTemplateName(SS
, T
->getTemplateName(),
6991 TL
.getTemplateNameLoc());
6992 if (Template
.isNull())
6995 return getDerived().TransformTemplateSpecializationType(TLB
, TL
, Template
);
6998 template<typename Derived
>
6999 QualType TreeTransform
<Derived
>::TransformAtomicType(TypeLocBuilder
&TLB
,
7001 QualType ValueType
= getDerived().TransformType(TLB
, TL
.getValueLoc());
7002 if (ValueType
.isNull())
7005 QualType Result
= TL
.getType();
7006 if (getDerived().AlwaysRebuild() ||
7007 ValueType
!= TL
.getValueLoc().getType()) {
7008 Result
= getDerived().RebuildAtomicType(ValueType
, TL
.getKWLoc());
7009 if (Result
.isNull())
7013 AtomicTypeLoc NewTL
= TLB
.push
<AtomicTypeLoc
>(Result
);
7014 NewTL
.setKWLoc(TL
.getKWLoc());
7015 NewTL
.setLParenLoc(TL
.getLParenLoc());
7016 NewTL
.setRParenLoc(TL
.getRParenLoc());
7021 template <typename Derived
>
7022 QualType TreeTransform
<Derived
>::TransformPipeType(TypeLocBuilder
&TLB
,
7024 QualType ValueType
= getDerived().TransformType(TLB
, TL
.getValueLoc());
7025 if (ValueType
.isNull())
7028 QualType Result
= TL
.getType();
7029 if (getDerived().AlwaysRebuild() || ValueType
!= TL
.getValueLoc().getType()) {
7030 const PipeType
*PT
= Result
->castAs
<PipeType
>();
7031 bool isReadPipe
= PT
->isReadOnly();
7032 Result
= getDerived().RebuildPipeType(ValueType
, TL
.getKWLoc(), isReadPipe
);
7033 if (Result
.isNull())
7037 PipeTypeLoc NewTL
= TLB
.push
<PipeTypeLoc
>(Result
);
7038 NewTL
.setKWLoc(TL
.getKWLoc());
7043 template <typename Derived
>
7044 QualType TreeTransform
<Derived
>::TransformBitIntType(TypeLocBuilder
&TLB
,
7046 const BitIntType
*EIT
= TL
.getTypePtr();
7047 QualType Result
= TL
.getType();
7049 if (getDerived().AlwaysRebuild()) {
7050 Result
= getDerived().RebuildBitIntType(EIT
->isUnsigned(),
7051 EIT
->getNumBits(), TL
.getNameLoc());
7052 if (Result
.isNull())
7056 BitIntTypeLoc NewTL
= TLB
.push
<BitIntTypeLoc
>(Result
);
7057 NewTL
.setNameLoc(TL
.getNameLoc());
7061 template <typename Derived
>
7062 QualType TreeTransform
<Derived
>::TransformDependentBitIntType(
7063 TypeLocBuilder
&TLB
, DependentBitIntTypeLoc TL
) {
7064 const DependentBitIntType
*EIT
= TL
.getTypePtr();
7066 EnterExpressionEvaluationContext
Unevaluated(
7067 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
7068 ExprResult BitsExpr
= getDerived().TransformExpr(EIT
->getNumBitsExpr());
7069 BitsExpr
= SemaRef
.ActOnConstantExpression(BitsExpr
);
7071 if (BitsExpr
.isInvalid())
7074 QualType Result
= TL
.getType();
7076 if (getDerived().AlwaysRebuild() || BitsExpr
.get() != EIT
->getNumBitsExpr()) {
7077 Result
= getDerived().RebuildDependentBitIntType(
7078 EIT
->isUnsigned(), BitsExpr
.get(), TL
.getNameLoc());
7080 if (Result
.isNull())
7084 if (isa
<DependentBitIntType
>(Result
)) {
7085 DependentBitIntTypeLoc NewTL
= TLB
.push
<DependentBitIntTypeLoc
>(Result
);
7086 NewTL
.setNameLoc(TL
.getNameLoc());
7088 BitIntTypeLoc NewTL
= TLB
.push
<BitIntTypeLoc
>(Result
);
7089 NewTL
.setNameLoc(TL
.getNameLoc());
7094 /// Simple iterator that traverses the template arguments in a
7095 /// container that provides a \c getArgLoc() member function.
7097 /// This iterator is intended to be used with the iterator form of
7098 /// \c TreeTransform<Derived>::TransformTemplateArguments().
7099 template<typename ArgLocContainer
>
7100 class TemplateArgumentLocContainerIterator
{
7101 ArgLocContainer
*Container
;
7105 typedef TemplateArgumentLoc value_type
;
7106 typedef TemplateArgumentLoc reference
;
7107 typedef int difference_type
;
7108 typedef std::input_iterator_tag iterator_category
;
7111 TemplateArgumentLoc Arg
;
7114 explicit pointer(TemplateArgumentLoc Arg
) : Arg(Arg
) { }
7116 const TemplateArgumentLoc
*operator->() const {
7122 TemplateArgumentLocContainerIterator() {}
7124 TemplateArgumentLocContainerIterator(ArgLocContainer
&Container
,
7126 : Container(&Container
), Index(Index
) { }
7128 TemplateArgumentLocContainerIterator
&operator++() {
7133 TemplateArgumentLocContainerIterator
operator++(int) {
7134 TemplateArgumentLocContainerIterator
Old(*this);
7139 TemplateArgumentLoc
operator*() const {
7140 return Container
->getArgLoc(Index
);
7143 pointer
operator->() const {
7144 return pointer(Container
->getArgLoc(Index
));
7147 friend bool operator==(const TemplateArgumentLocContainerIterator
&X
,
7148 const TemplateArgumentLocContainerIterator
&Y
) {
7149 return X
.Container
== Y
.Container
&& X
.Index
== Y
.Index
;
7152 friend bool operator!=(const TemplateArgumentLocContainerIterator
&X
,
7153 const TemplateArgumentLocContainerIterator
&Y
) {
7158 template<typename Derived
>
7159 QualType TreeTransform
<Derived
>::TransformAutoType(TypeLocBuilder
&TLB
,
7161 const AutoType
*T
= TL
.getTypePtr();
7162 QualType OldDeduced
= T
->getDeducedType();
7163 QualType NewDeduced
;
7164 if (!OldDeduced
.isNull()) {
7165 NewDeduced
= getDerived().TransformType(OldDeduced
);
7166 if (NewDeduced
.isNull())
7170 ConceptDecl
*NewCD
= nullptr;
7171 TemplateArgumentListInfo NewTemplateArgs
;
7172 NestedNameSpecifierLoc NewNestedNameSpec
;
7173 if (T
->isConstrained()) {
7174 assert(TL
.getConceptReference());
7175 NewCD
= cast_or_null
<ConceptDecl
>(getDerived().TransformDecl(
7176 TL
.getConceptNameLoc(), T
->getTypeConstraintConcept()));
7178 NewTemplateArgs
.setLAngleLoc(TL
.getLAngleLoc());
7179 NewTemplateArgs
.setRAngleLoc(TL
.getRAngleLoc());
7180 typedef TemplateArgumentLocContainerIterator
<AutoTypeLoc
> ArgIterator
;
7181 if (getDerived().TransformTemplateArguments(
7182 ArgIterator(TL
, 0), ArgIterator(TL
, TL
.getNumArgs()),
7186 if (TL
.getNestedNameSpecifierLoc()) {
7188 = getDerived().TransformNestedNameSpecifierLoc(
7189 TL
.getNestedNameSpecifierLoc());
7190 if (!NewNestedNameSpec
)
7195 QualType Result
= TL
.getType();
7196 if (getDerived().AlwaysRebuild() || NewDeduced
!= OldDeduced
||
7197 T
->isDependentType() || T
->isConstrained()) {
7198 // FIXME: Maybe don't rebuild if all template arguments are the same.
7199 llvm::SmallVector
<TemplateArgument
, 4> NewArgList
;
7200 NewArgList
.reserve(NewTemplateArgs
.size());
7201 for (const auto &ArgLoc
: NewTemplateArgs
.arguments())
7202 NewArgList
.push_back(ArgLoc
.getArgument());
7203 Result
= getDerived().RebuildAutoType(NewDeduced
, T
->getKeyword(), NewCD
,
7205 if (Result
.isNull())
7209 AutoTypeLoc NewTL
= TLB
.push
<AutoTypeLoc
>(Result
);
7210 NewTL
.setNameLoc(TL
.getNameLoc());
7211 NewTL
.setRParenLoc(TL
.getRParenLoc());
7212 NewTL
.setConceptReference(nullptr);
7214 if (T
->isConstrained()) {
7215 DeclarationNameInfo DNI
= DeclarationNameInfo(
7216 TL
.getTypePtr()->getTypeConstraintConcept()->getDeclName(),
7217 TL
.getConceptNameLoc(),
7218 TL
.getTypePtr()->getTypeConstraintConcept()->getDeclName());
7219 auto *CR
= ConceptReference::Create(
7220 SemaRef
.Context
, NewNestedNameSpec
, TL
.getTemplateKWLoc(), DNI
,
7221 TL
.getFoundDecl(), TL
.getTypePtr()->getTypeConstraintConcept(),
7222 ASTTemplateArgumentListInfo::Create(SemaRef
.Context
, NewTemplateArgs
));
7223 NewTL
.setConceptReference(CR
);
7229 template <typename Derived
>
7230 QualType TreeTransform
<Derived
>::TransformTemplateSpecializationType(
7231 TypeLocBuilder
&TLB
,
7232 TemplateSpecializationTypeLoc TL
,
7233 TemplateName Template
) {
7234 TemplateArgumentListInfo NewTemplateArgs
;
7235 NewTemplateArgs
.setLAngleLoc(TL
.getLAngleLoc());
7236 NewTemplateArgs
.setRAngleLoc(TL
.getRAngleLoc());
7237 typedef TemplateArgumentLocContainerIterator
<TemplateSpecializationTypeLoc
>
7239 if (getDerived().TransformTemplateArguments(ArgIterator(TL
, 0),
7240 ArgIterator(TL
, TL
.getNumArgs()),
7244 // FIXME: maybe don't rebuild if all the template arguments are the same.
7247 getDerived().RebuildTemplateSpecializationType(Template
,
7248 TL
.getTemplateNameLoc(),
7251 if (!Result
.isNull()) {
7252 // Specializations of template template parameters are represented as
7253 // TemplateSpecializationTypes, and substitution of type alias templates
7254 // within a dependent context can transform them into
7255 // DependentTemplateSpecializationTypes.
7256 if (isa
<DependentTemplateSpecializationType
>(Result
)) {
7257 DependentTemplateSpecializationTypeLoc NewTL
7258 = TLB
.push
<DependentTemplateSpecializationTypeLoc
>(Result
);
7259 NewTL
.setElaboratedKeywordLoc(SourceLocation());
7260 NewTL
.setQualifierLoc(NestedNameSpecifierLoc());
7261 NewTL
.setTemplateKeywordLoc(TL
.getTemplateKeywordLoc());
7262 NewTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
7263 NewTL
.setLAngleLoc(TL
.getLAngleLoc());
7264 NewTL
.setRAngleLoc(TL
.getRAngleLoc());
7265 for (unsigned i
= 0, e
= NewTemplateArgs
.size(); i
!= e
; ++i
)
7266 NewTL
.setArgLocInfo(i
, NewTemplateArgs
[i
].getLocInfo());
7270 TemplateSpecializationTypeLoc NewTL
7271 = TLB
.push
<TemplateSpecializationTypeLoc
>(Result
);
7272 NewTL
.setTemplateKeywordLoc(TL
.getTemplateKeywordLoc());
7273 NewTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
7274 NewTL
.setLAngleLoc(TL
.getLAngleLoc());
7275 NewTL
.setRAngleLoc(TL
.getRAngleLoc());
7276 for (unsigned i
= 0, e
= NewTemplateArgs
.size(); i
!= e
; ++i
)
7277 NewTL
.setArgLocInfo(i
, NewTemplateArgs
[i
].getLocInfo());
7283 template <typename Derived
>
7284 QualType TreeTransform
<Derived
>::TransformDependentTemplateSpecializationType(
7285 TypeLocBuilder
&TLB
,
7286 DependentTemplateSpecializationTypeLoc TL
,
7287 TemplateName Template
,
7289 TemplateArgumentListInfo NewTemplateArgs
;
7290 NewTemplateArgs
.setLAngleLoc(TL
.getLAngleLoc());
7291 NewTemplateArgs
.setRAngleLoc(TL
.getRAngleLoc());
7292 typedef TemplateArgumentLocContainerIterator
<
7293 DependentTemplateSpecializationTypeLoc
> ArgIterator
;
7294 if (getDerived().TransformTemplateArguments(ArgIterator(TL
, 0),
7295 ArgIterator(TL
, TL
.getNumArgs()),
7299 // FIXME: maybe don't rebuild if all the template arguments are the same.
7301 if (DependentTemplateName
*DTN
= Template
.getAsDependentTemplateName()) {
7302 QualType Result
= getSema().Context
.getDependentTemplateSpecializationType(
7303 TL
.getTypePtr()->getKeyword(), DTN
->getQualifier(),
7304 DTN
->getIdentifier(), NewTemplateArgs
.arguments());
7306 DependentTemplateSpecializationTypeLoc NewTL
7307 = TLB
.push
<DependentTemplateSpecializationTypeLoc
>(Result
);
7308 NewTL
.setElaboratedKeywordLoc(TL
.getElaboratedKeywordLoc());
7309 NewTL
.setQualifierLoc(SS
.getWithLocInContext(SemaRef
.Context
));
7310 NewTL
.setTemplateKeywordLoc(TL
.getTemplateKeywordLoc());
7311 NewTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
7312 NewTL
.setLAngleLoc(TL
.getLAngleLoc());
7313 NewTL
.setRAngleLoc(TL
.getRAngleLoc());
7314 for (unsigned i
= 0, e
= NewTemplateArgs
.size(); i
!= e
; ++i
)
7315 NewTL
.setArgLocInfo(i
, NewTemplateArgs
[i
].getLocInfo());
7320 = getDerived().RebuildTemplateSpecializationType(Template
,
7321 TL
.getTemplateNameLoc(),
7324 if (!Result
.isNull()) {
7325 /// FIXME: Wrap this in an elaborated-type-specifier?
7326 TemplateSpecializationTypeLoc NewTL
7327 = TLB
.push
<TemplateSpecializationTypeLoc
>(Result
);
7328 NewTL
.setTemplateKeywordLoc(TL
.getTemplateKeywordLoc());
7329 NewTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
7330 NewTL
.setLAngleLoc(TL
.getLAngleLoc());
7331 NewTL
.setRAngleLoc(TL
.getRAngleLoc());
7332 for (unsigned i
= 0, e
= NewTemplateArgs
.size(); i
!= e
; ++i
)
7333 NewTL
.setArgLocInfo(i
, NewTemplateArgs
[i
].getLocInfo());
7339 template<typename Derived
>
7341 TreeTransform
<Derived
>::TransformElaboratedType(TypeLocBuilder
&TLB
,
7342 ElaboratedTypeLoc TL
) {
7343 const ElaboratedType
*T
= TL
.getTypePtr();
7345 NestedNameSpecifierLoc QualifierLoc
;
7346 // NOTE: the qualifier in an ElaboratedType is optional.
7347 if (TL
.getQualifierLoc()) {
7349 = getDerived().TransformNestedNameSpecifierLoc(TL
.getQualifierLoc());
7354 QualType NamedT
= getDerived().TransformType(TLB
, TL
.getNamedTypeLoc());
7355 if (NamedT
.isNull())
7358 // C++0x [dcl.type.elab]p2:
7359 // If the identifier resolves to a typedef-name or the simple-template-id
7360 // resolves to an alias template specialization, the
7361 // elaborated-type-specifier is ill-formed.
7362 if (T
->getKeyword() != ElaboratedTypeKeyword::None
&&
7363 T
->getKeyword() != ElaboratedTypeKeyword::Typename
) {
7364 if (const TemplateSpecializationType
*TST
=
7365 NamedT
->getAs
<TemplateSpecializationType
>()) {
7366 TemplateName Template
= TST
->getTemplateName();
7367 if (TypeAliasTemplateDecl
*TAT
= dyn_cast_or_null
<TypeAliasTemplateDecl
>(
7368 Template
.getAsTemplateDecl())) {
7369 SemaRef
.Diag(TL
.getNamedTypeLoc().getBeginLoc(),
7370 diag::err_tag_reference_non_tag
)
7371 << TAT
<< Sema::NTK_TypeAliasTemplate
7372 << llvm::to_underlying(
7373 ElaboratedType::getTagTypeKindForKeyword(T
->getKeyword()));
7374 SemaRef
.Diag(TAT
->getLocation(), diag::note_declared_at
);
7379 QualType Result
= TL
.getType();
7380 if (getDerived().AlwaysRebuild() ||
7381 QualifierLoc
!= TL
.getQualifierLoc() ||
7382 NamedT
!= T
->getNamedType()) {
7383 Result
= getDerived().RebuildElaboratedType(TL
.getElaboratedKeywordLoc(),
7385 QualifierLoc
, NamedT
);
7386 if (Result
.isNull())
7390 ElaboratedTypeLoc NewTL
= TLB
.push
<ElaboratedTypeLoc
>(Result
);
7391 NewTL
.setElaboratedKeywordLoc(TL
.getElaboratedKeywordLoc());
7392 NewTL
.setQualifierLoc(QualifierLoc
);
7396 template <typename Derived
>
7397 QualType TreeTransform
<Derived
>::TransformAttributedType(TypeLocBuilder
&TLB
,
7398 AttributedTypeLoc TL
) {
7399 const AttributedType
*oldType
= TL
.getTypePtr();
7400 QualType modifiedType
= getDerived().TransformType(TLB
, TL
.getModifiedLoc());
7401 if (modifiedType
.isNull())
7404 // oldAttr can be null if we started with a QualType rather than a TypeLoc.
7405 const Attr
*oldAttr
= TL
.getAttr();
7406 const Attr
*newAttr
= oldAttr
? getDerived().TransformAttr(oldAttr
) : nullptr;
7407 if (oldAttr
&& !newAttr
)
7410 QualType result
= TL
.getType();
7412 // FIXME: dependent operand expressions?
7413 if (getDerived().AlwaysRebuild() ||
7414 modifiedType
!= oldType
->getModifiedType()) {
7415 // If the equivalent type is equal to the modified type, we don't want to
7416 // transform it as well because:
7418 // 1. The transformation would yield the same result and is therefore
7421 // 2. Transforming the same type twice can cause problems, e.g. if it
7422 // is a FunctionProtoType, we may end up instantiating the function
7423 // parameters twice, which causes an assertion since the parameters
7424 // are already bound to their counterparts in the template for this
7427 QualType equivalentType
= modifiedType
;
7428 if (TL
.getModifiedLoc().getType() != TL
.getEquivalentTypeLoc().getType()) {
7429 TypeLocBuilder AuxiliaryTLB
;
7430 AuxiliaryTLB
.reserve(TL
.getFullDataSize());
7432 getDerived().TransformType(AuxiliaryTLB
, TL
.getEquivalentTypeLoc());
7433 if (equivalentType
.isNull())
7437 // Check whether we can add nullability; it is only represented as
7438 // type sugar, and therefore cannot be diagnosed in any other way.
7439 if (auto nullability
= oldType
->getImmediateNullability()) {
7440 if (!modifiedType
->canHaveNullability()) {
7441 SemaRef
.Diag((TL
.getAttr() ? TL
.getAttr()->getLocation()
7442 : TL
.getModifiedLoc().getBeginLoc()),
7443 diag::err_nullability_nonpointer
)
7444 << DiagNullabilityKind(*nullability
, false) << modifiedType
;
7449 result
= SemaRef
.Context
.getAttributedType(TL
.getAttrKind(),
7455 AttributedTypeLoc newTL
= TLB
.push
<AttributedTypeLoc
>(result
);
7456 newTL
.setAttr(newAttr
);
7460 template <typename Derived
>
7461 QualType TreeTransform
<Derived
>::TransformCountAttributedType(
7462 TypeLocBuilder
&TLB
, CountAttributedTypeLoc TL
) {
7463 const CountAttributedType
*OldTy
= TL
.getTypePtr();
7464 QualType InnerTy
= getDerived().TransformType(TLB
, TL
.getInnerLoc());
7465 if (InnerTy
.isNull())
7468 Expr
*OldCount
= TL
.getCountExpr();
7469 Expr
*NewCount
= nullptr;
7471 ExprResult CountResult
= getDerived().TransformExpr(OldCount
);
7472 if (CountResult
.isInvalid())
7474 NewCount
= CountResult
.get();
7477 QualType Result
= TL
.getType();
7478 if (getDerived().AlwaysRebuild() || InnerTy
!= OldTy
->desugar() ||
7479 OldCount
!= NewCount
) {
7480 // Currently, CountAttributedType can only wrap incomplete array types.
7481 Result
= SemaRef
.BuildCountAttributedArrayOrPointerType(
7482 InnerTy
, NewCount
, OldTy
->isCountInBytes(), OldTy
->isOrNull());
7485 TLB
.push
<CountAttributedTypeLoc
>(Result
);
7489 template <typename Derived
>
7490 QualType TreeTransform
<Derived
>::TransformBTFTagAttributedType(
7491 TypeLocBuilder
&TLB
, BTFTagAttributedTypeLoc TL
) {
7492 // The BTFTagAttributedType is available for C only.
7493 llvm_unreachable("Unexpected TreeTransform for BTFTagAttributedType");
7496 template <typename Derived
>
7497 QualType TreeTransform
<Derived
>::TransformHLSLAttributedResourceType(
7498 TypeLocBuilder
&TLB
, HLSLAttributedResourceTypeLoc TL
) {
7500 const HLSLAttributedResourceType
*oldType
= TL
.getTypePtr();
7502 QualType WrappedTy
= getDerived().TransformType(TLB
, TL
.getWrappedLoc());
7503 if (WrappedTy
.isNull())
7506 QualType ContainedTy
= QualType();
7507 QualType OldContainedTy
= oldType
->getContainedType();
7508 if (!OldContainedTy
.isNull()) {
7509 TypeSourceInfo
*oldContainedTSI
= TL
.getContainedTypeSourceInfo();
7510 if (!oldContainedTSI
)
7511 oldContainedTSI
= getSema().getASTContext().getTrivialTypeSourceInfo(
7512 OldContainedTy
, SourceLocation());
7513 TypeSourceInfo
*ContainedTSI
= getDerived().TransformType(oldContainedTSI
);
7516 ContainedTy
= ContainedTSI
->getType();
7519 QualType Result
= TL
.getType();
7520 if (getDerived().AlwaysRebuild() || WrappedTy
!= oldType
->getWrappedType() ||
7521 ContainedTy
!= oldType
->getContainedType()) {
7522 Result
= SemaRef
.Context
.getHLSLAttributedResourceType(
7523 WrappedTy
, ContainedTy
, oldType
->getAttrs());
7526 TLB
.push
<HLSLAttributedResourceTypeLoc
>(Result
);
7530 template<typename Derived
>
7532 TreeTransform
<Derived
>::TransformParenType(TypeLocBuilder
&TLB
,
7534 QualType Inner
= getDerived().TransformType(TLB
, TL
.getInnerLoc());
7538 QualType Result
= TL
.getType();
7539 if (getDerived().AlwaysRebuild() ||
7540 Inner
!= TL
.getInnerLoc().getType()) {
7541 Result
= getDerived().RebuildParenType(Inner
);
7542 if (Result
.isNull())
7546 ParenTypeLoc NewTL
= TLB
.push
<ParenTypeLoc
>(Result
);
7547 NewTL
.setLParenLoc(TL
.getLParenLoc());
7548 NewTL
.setRParenLoc(TL
.getRParenLoc());
7552 template <typename Derived
>
7554 TreeTransform
<Derived
>::TransformMacroQualifiedType(TypeLocBuilder
&TLB
,
7555 MacroQualifiedTypeLoc TL
) {
7556 QualType Inner
= getDerived().TransformType(TLB
, TL
.getInnerLoc());
7560 QualType Result
= TL
.getType();
7561 if (getDerived().AlwaysRebuild() || Inner
!= TL
.getInnerLoc().getType()) {
7563 getDerived().RebuildMacroQualifiedType(Inner
, TL
.getMacroIdentifier());
7564 if (Result
.isNull())
7568 MacroQualifiedTypeLoc NewTL
= TLB
.push
<MacroQualifiedTypeLoc
>(Result
);
7569 NewTL
.setExpansionLoc(TL
.getExpansionLoc());
7573 template<typename Derived
>
7574 QualType TreeTransform
<Derived
>::TransformDependentNameType(
7575 TypeLocBuilder
&TLB
, DependentNameTypeLoc TL
) {
7576 return TransformDependentNameType(TLB
, TL
, false);
7579 template<typename Derived
>
7580 QualType TreeTransform
<Derived
>::TransformDependentNameType(
7581 TypeLocBuilder
&TLB
, DependentNameTypeLoc TL
, bool DeducedTSTContext
) {
7582 const DependentNameType
*T
= TL
.getTypePtr();
7584 NestedNameSpecifierLoc QualifierLoc
7585 = getDerived().TransformNestedNameSpecifierLoc(TL
.getQualifierLoc());
7590 = getDerived().RebuildDependentNameType(T
->getKeyword(),
7591 TL
.getElaboratedKeywordLoc(),
7596 if (Result
.isNull())
7599 if (const ElaboratedType
* ElabT
= Result
->getAs
<ElaboratedType
>()) {
7600 QualType NamedT
= ElabT
->getNamedType();
7601 TLB
.pushTypeSpec(NamedT
).setNameLoc(TL
.getNameLoc());
7603 ElaboratedTypeLoc NewTL
= TLB
.push
<ElaboratedTypeLoc
>(Result
);
7604 NewTL
.setElaboratedKeywordLoc(TL
.getElaboratedKeywordLoc());
7605 NewTL
.setQualifierLoc(QualifierLoc
);
7607 DependentNameTypeLoc NewTL
= TLB
.push
<DependentNameTypeLoc
>(Result
);
7608 NewTL
.setElaboratedKeywordLoc(TL
.getElaboratedKeywordLoc());
7609 NewTL
.setQualifierLoc(QualifierLoc
);
7610 NewTL
.setNameLoc(TL
.getNameLoc());
7615 template<typename Derived
>
7616 QualType TreeTransform
<Derived
>::
7617 TransformDependentTemplateSpecializationType(TypeLocBuilder
&TLB
,
7618 DependentTemplateSpecializationTypeLoc TL
) {
7619 NestedNameSpecifierLoc QualifierLoc
;
7620 if (TL
.getQualifierLoc()) {
7622 = getDerived().TransformNestedNameSpecifierLoc(TL
.getQualifierLoc());
7628 .TransformDependentTemplateSpecializationType(TLB
, TL
, QualifierLoc
);
7631 template<typename Derived
>
7632 QualType TreeTransform
<Derived
>::
7633 TransformDependentTemplateSpecializationType(TypeLocBuilder
&TLB
,
7634 DependentTemplateSpecializationTypeLoc TL
,
7635 NestedNameSpecifierLoc QualifierLoc
) {
7636 const DependentTemplateSpecializationType
*T
= TL
.getTypePtr();
7638 TemplateArgumentListInfo NewTemplateArgs
;
7639 NewTemplateArgs
.setLAngleLoc(TL
.getLAngleLoc());
7640 NewTemplateArgs
.setRAngleLoc(TL
.getRAngleLoc());
7642 typedef TemplateArgumentLocContainerIterator
<
7643 DependentTemplateSpecializationTypeLoc
> ArgIterator
;
7644 if (getDerived().TransformTemplateArguments(ArgIterator(TL
, 0),
7645 ArgIterator(TL
, TL
.getNumArgs()),
7649 QualType Result
= getDerived().RebuildDependentTemplateSpecializationType(
7650 T
->getKeyword(), QualifierLoc
, TL
.getTemplateKeywordLoc(),
7651 T
->getIdentifier(), TL
.getTemplateNameLoc(), NewTemplateArgs
,
7652 /*AllowInjectedClassName*/ false);
7653 if (Result
.isNull())
7656 if (const ElaboratedType
*ElabT
= dyn_cast
<ElaboratedType
>(Result
)) {
7657 QualType NamedT
= ElabT
->getNamedType();
7659 // Copy information relevant to the template specialization.
7660 TemplateSpecializationTypeLoc NamedTL
7661 = TLB
.push
<TemplateSpecializationTypeLoc
>(NamedT
);
7662 NamedTL
.setTemplateKeywordLoc(TL
.getTemplateKeywordLoc());
7663 NamedTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
7664 NamedTL
.setLAngleLoc(TL
.getLAngleLoc());
7665 NamedTL
.setRAngleLoc(TL
.getRAngleLoc());
7666 for (unsigned I
= 0, E
= NewTemplateArgs
.size(); I
!= E
; ++I
)
7667 NamedTL
.setArgLocInfo(I
, NewTemplateArgs
[I
].getLocInfo());
7669 // Copy information relevant to the elaborated type.
7670 ElaboratedTypeLoc NewTL
= TLB
.push
<ElaboratedTypeLoc
>(Result
);
7671 NewTL
.setElaboratedKeywordLoc(TL
.getElaboratedKeywordLoc());
7672 NewTL
.setQualifierLoc(QualifierLoc
);
7673 } else if (isa
<DependentTemplateSpecializationType
>(Result
)) {
7674 DependentTemplateSpecializationTypeLoc SpecTL
7675 = TLB
.push
<DependentTemplateSpecializationTypeLoc
>(Result
);
7676 SpecTL
.setElaboratedKeywordLoc(TL
.getElaboratedKeywordLoc());
7677 SpecTL
.setQualifierLoc(QualifierLoc
);
7678 SpecTL
.setTemplateKeywordLoc(TL
.getTemplateKeywordLoc());
7679 SpecTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
7680 SpecTL
.setLAngleLoc(TL
.getLAngleLoc());
7681 SpecTL
.setRAngleLoc(TL
.getRAngleLoc());
7682 for (unsigned I
= 0, E
= NewTemplateArgs
.size(); I
!= E
; ++I
)
7683 SpecTL
.setArgLocInfo(I
, NewTemplateArgs
[I
].getLocInfo());
7685 TemplateSpecializationTypeLoc SpecTL
7686 = TLB
.push
<TemplateSpecializationTypeLoc
>(Result
);
7687 SpecTL
.setTemplateKeywordLoc(TL
.getTemplateKeywordLoc());
7688 SpecTL
.setTemplateNameLoc(TL
.getTemplateNameLoc());
7689 SpecTL
.setLAngleLoc(TL
.getLAngleLoc());
7690 SpecTL
.setRAngleLoc(TL
.getRAngleLoc());
7691 for (unsigned I
= 0, E
= NewTemplateArgs
.size(); I
!= E
; ++I
)
7692 SpecTL
.setArgLocInfo(I
, NewTemplateArgs
[I
].getLocInfo());
7697 template<typename Derived
>
7698 QualType TreeTransform
<Derived
>::TransformPackExpansionType(TypeLocBuilder
&TLB
,
7699 PackExpansionTypeLoc TL
) {
7701 = getDerived().TransformType(TLB
, TL
.getPatternLoc());
7702 if (Pattern
.isNull())
7705 QualType Result
= TL
.getType();
7706 if (getDerived().AlwaysRebuild() ||
7707 Pattern
!= TL
.getPatternLoc().getType()) {
7708 Result
= getDerived().RebuildPackExpansionType(Pattern
,
7709 TL
.getPatternLoc().getSourceRange(),
7710 TL
.getEllipsisLoc(),
7711 TL
.getTypePtr()->getNumExpansions());
7712 if (Result
.isNull())
7716 PackExpansionTypeLoc NewT
= TLB
.push
<PackExpansionTypeLoc
>(Result
);
7717 NewT
.setEllipsisLoc(TL
.getEllipsisLoc());
7721 template<typename Derived
>
7723 TreeTransform
<Derived
>::TransformObjCInterfaceType(TypeLocBuilder
&TLB
,
7724 ObjCInterfaceTypeLoc TL
) {
7725 // ObjCInterfaceType is never dependent.
7726 TLB
.pushFullCopy(TL
);
7727 return TL
.getType();
7730 template<typename Derived
>
7732 TreeTransform
<Derived
>::TransformObjCTypeParamType(TypeLocBuilder
&TLB
,
7733 ObjCTypeParamTypeLoc TL
) {
7734 const ObjCTypeParamType
*T
= TL
.getTypePtr();
7735 ObjCTypeParamDecl
*OTP
= cast_or_null
<ObjCTypeParamDecl
>(
7736 getDerived().TransformDecl(T
->getDecl()->getLocation(), T
->getDecl()));
7740 QualType Result
= TL
.getType();
7741 if (getDerived().AlwaysRebuild() ||
7742 OTP
!= T
->getDecl()) {
7743 Result
= getDerived().RebuildObjCTypeParamType(
7744 OTP
, TL
.getProtocolLAngleLoc(),
7745 llvm::ArrayRef(TL
.getTypePtr()->qual_begin(), TL
.getNumProtocols()),
7746 TL
.getProtocolLocs(), TL
.getProtocolRAngleLoc());
7747 if (Result
.isNull())
7751 ObjCTypeParamTypeLoc NewTL
= TLB
.push
<ObjCTypeParamTypeLoc
>(Result
);
7752 if (TL
.getNumProtocols()) {
7753 NewTL
.setProtocolLAngleLoc(TL
.getProtocolLAngleLoc());
7754 for (unsigned i
= 0, n
= TL
.getNumProtocols(); i
!= n
; ++i
)
7755 NewTL
.setProtocolLoc(i
, TL
.getProtocolLoc(i
));
7756 NewTL
.setProtocolRAngleLoc(TL
.getProtocolRAngleLoc());
7761 template<typename Derived
>
7763 TreeTransform
<Derived
>::TransformObjCObjectType(TypeLocBuilder
&TLB
,
7764 ObjCObjectTypeLoc TL
) {
7765 // Transform base type.
7766 QualType BaseType
= getDerived().TransformType(TLB
, TL
.getBaseLoc());
7767 if (BaseType
.isNull())
7770 bool AnyChanged
= BaseType
!= TL
.getBaseLoc().getType();
7772 // Transform type arguments.
7773 SmallVector
<TypeSourceInfo
*, 4> NewTypeArgInfos
;
7774 for (unsigned i
= 0, n
= TL
.getNumTypeArgs(); i
!= n
; ++i
) {
7775 TypeSourceInfo
*TypeArgInfo
= TL
.getTypeArgTInfo(i
);
7776 TypeLoc TypeArgLoc
= TypeArgInfo
->getTypeLoc();
7777 QualType TypeArg
= TypeArgInfo
->getType();
7778 if (auto PackExpansionLoc
= TypeArgLoc
.getAs
<PackExpansionTypeLoc
>()) {
7781 // We have a pack expansion. Instantiate it.
7782 const auto *PackExpansion
= PackExpansionLoc
.getType()
7783 ->castAs
<PackExpansionType
>();
7784 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
7785 SemaRef
.collectUnexpandedParameterPacks(PackExpansion
->getPattern(),
7787 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
7789 // Determine whether the set of unexpanded parameter packs can
7790 // and should be expanded.
7791 TypeLoc PatternLoc
= PackExpansionLoc
.getPatternLoc();
7792 bool Expand
= false;
7793 bool RetainExpansion
= false;
7794 std::optional
<unsigned> NumExpansions
= PackExpansion
->getNumExpansions();
7795 if (getDerived().TryExpandParameterPacks(
7796 PackExpansionLoc
.getEllipsisLoc(), PatternLoc
.getSourceRange(),
7797 Unexpanded
, Expand
, RetainExpansion
, NumExpansions
))
7801 // We can't expand this pack expansion into separate arguments yet;
7802 // just substitute into the pattern and create a new pack expansion
7804 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
7806 TypeLocBuilder TypeArgBuilder
;
7807 TypeArgBuilder
.reserve(PatternLoc
.getFullDataSize());
7808 QualType NewPatternType
= getDerived().TransformType(TypeArgBuilder
,
7810 if (NewPatternType
.isNull())
7813 QualType NewExpansionType
= SemaRef
.Context
.getPackExpansionType(
7814 NewPatternType
, NumExpansions
);
7815 auto NewExpansionLoc
= TLB
.push
<PackExpansionTypeLoc
>(NewExpansionType
);
7816 NewExpansionLoc
.setEllipsisLoc(PackExpansionLoc
.getEllipsisLoc());
7817 NewTypeArgInfos
.push_back(
7818 TypeArgBuilder
.getTypeSourceInfo(SemaRef
.Context
, NewExpansionType
));
7822 // Substitute into the pack expansion pattern for each slice of the
7824 for (unsigned ArgIdx
= 0; ArgIdx
!= *NumExpansions
; ++ArgIdx
) {
7825 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), ArgIdx
);
7827 TypeLocBuilder TypeArgBuilder
;
7828 TypeArgBuilder
.reserve(PatternLoc
.getFullDataSize());
7830 QualType NewTypeArg
= getDerived().TransformType(TypeArgBuilder
,
7832 if (NewTypeArg
.isNull())
7835 NewTypeArgInfos
.push_back(
7836 TypeArgBuilder
.getTypeSourceInfo(SemaRef
.Context
, NewTypeArg
));
7842 TypeLocBuilder TypeArgBuilder
;
7843 TypeArgBuilder
.reserve(TypeArgLoc
.getFullDataSize());
7844 QualType NewTypeArg
=
7845 getDerived().TransformType(TypeArgBuilder
, TypeArgLoc
);
7846 if (NewTypeArg
.isNull())
7849 // If nothing changed, just keep the old TypeSourceInfo.
7850 if (NewTypeArg
== TypeArg
) {
7851 NewTypeArgInfos
.push_back(TypeArgInfo
);
7855 NewTypeArgInfos
.push_back(
7856 TypeArgBuilder
.getTypeSourceInfo(SemaRef
.Context
, NewTypeArg
));
7860 QualType Result
= TL
.getType();
7861 if (getDerived().AlwaysRebuild() || AnyChanged
) {
7862 // Rebuild the type.
7863 Result
= getDerived().RebuildObjCObjectType(
7864 BaseType
, TL
.getBeginLoc(), TL
.getTypeArgsLAngleLoc(), NewTypeArgInfos
,
7865 TL
.getTypeArgsRAngleLoc(), TL
.getProtocolLAngleLoc(),
7866 llvm::ArrayRef(TL
.getTypePtr()->qual_begin(), TL
.getNumProtocols()),
7867 TL
.getProtocolLocs(), TL
.getProtocolRAngleLoc());
7869 if (Result
.isNull())
7873 ObjCObjectTypeLoc NewT
= TLB
.push
<ObjCObjectTypeLoc
>(Result
);
7874 NewT
.setHasBaseTypeAsWritten(true);
7875 NewT
.setTypeArgsLAngleLoc(TL
.getTypeArgsLAngleLoc());
7876 for (unsigned i
= 0, n
= TL
.getNumTypeArgs(); i
!= n
; ++i
)
7877 NewT
.setTypeArgTInfo(i
, NewTypeArgInfos
[i
]);
7878 NewT
.setTypeArgsRAngleLoc(TL
.getTypeArgsRAngleLoc());
7879 NewT
.setProtocolLAngleLoc(TL
.getProtocolLAngleLoc());
7880 for (unsigned i
= 0, n
= TL
.getNumProtocols(); i
!= n
; ++i
)
7881 NewT
.setProtocolLoc(i
, TL
.getProtocolLoc(i
));
7882 NewT
.setProtocolRAngleLoc(TL
.getProtocolRAngleLoc());
7886 template<typename Derived
>
7888 TreeTransform
<Derived
>::TransformObjCObjectPointerType(TypeLocBuilder
&TLB
,
7889 ObjCObjectPointerTypeLoc TL
) {
7890 QualType PointeeType
= getDerived().TransformType(TLB
, TL
.getPointeeLoc());
7891 if (PointeeType
.isNull())
7894 QualType Result
= TL
.getType();
7895 if (getDerived().AlwaysRebuild() ||
7896 PointeeType
!= TL
.getPointeeLoc().getType()) {
7897 Result
= getDerived().RebuildObjCObjectPointerType(PointeeType
,
7899 if (Result
.isNull())
7903 ObjCObjectPointerTypeLoc NewT
= TLB
.push
<ObjCObjectPointerTypeLoc
>(Result
);
7904 NewT
.setStarLoc(TL
.getStarLoc());
7908 //===----------------------------------------------------------------------===//
7909 // Statement transformation
7910 //===----------------------------------------------------------------------===//
7911 template<typename Derived
>
7913 TreeTransform
<Derived
>::TransformNullStmt(NullStmt
*S
) {
7917 template<typename Derived
>
7919 TreeTransform
<Derived
>::TransformCompoundStmt(CompoundStmt
*S
) {
7920 return getDerived().TransformCompoundStmt(S
, false);
7923 template<typename Derived
>
7925 TreeTransform
<Derived
>::TransformCompoundStmt(CompoundStmt
*S
,
7927 Sema::CompoundScopeRAII
CompoundScope(getSema());
7928 Sema::FPFeaturesStateRAII
FPSave(getSema());
7929 if (S
->hasStoredFPFeatures())
7930 getSema().resetFPOptions(
7931 S
->getStoredFPFeatures().applyOverrides(getSema().getLangOpts()));
7933 const Stmt
*ExprResult
= S
->getStmtExprResult();
7934 bool SubStmtInvalid
= false;
7935 bool SubStmtChanged
= false;
7936 SmallVector
<Stmt
*, 8> Statements
;
7937 for (auto *B
: S
->body()) {
7938 StmtResult Result
= getDerived().TransformStmt(
7939 B
, IsStmtExpr
&& B
== ExprResult
? SDK_StmtExprResult
: SDK_Discarded
);
7941 if (Result
.isInvalid()) {
7942 // Immediately fail if this was a DeclStmt, since it's very
7943 // likely that this will cause problems for future statements.
7944 if (isa
<DeclStmt
>(B
))
7947 // Otherwise, just keep processing substatements and fail later.
7948 SubStmtInvalid
= true;
7952 SubStmtChanged
= SubStmtChanged
|| Result
.get() != B
;
7953 Statements
.push_back(Result
.getAs
<Stmt
>());
7959 if (!getDerived().AlwaysRebuild() &&
7963 return getDerived().RebuildCompoundStmt(S
->getLBracLoc(),
7969 template<typename Derived
>
7971 TreeTransform
<Derived
>::TransformCaseStmt(CaseStmt
*S
) {
7972 ExprResult LHS
, RHS
;
7974 EnterExpressionEvaluationContext
Unevaluated(
7975 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
7977 // Transform the left-hand case value.
7978 LHS
= getDerived().TransformExpr(S
->getLHS());
7979 LHS
= SemaRef
.ActOnCaseExpr(S
->getCaseLoc(), LHS
);
7980 if (LHS
.isInvalid())
7983 // Transform the right-hand case value (for the GNU case-range extension).
7984 RHS
= getDerived().TransformExpr(S
->getRHS());
7985 RHS
= SemaRef
.ActOnCaseExpr(S
->getCaseLoc(), RHS
);
7986 if (RHS
.isInvalid())
7990 // Build the case statement.
7991 // Case statements are always rebuilt so that they will attached to their
7992 // transformed switch statement.
7993 StmtResult Case
= getDerived().RebuildCaseStmt(S
->getCaseLoc(),
7995 S
->getEllipsisLoc(),
7998 if (Case
.isInvalid())
8001 // Transform the statement following the case
8002 StmtResult SubStmt
=
8003 getDerived().TransformStmt(S
->getSubStmt());
8004 if (SubStmt
.isInvalid())
8007 // Attach the body to the case statement
8008 return getDerived().RebuildCaseStmtBody(Case
.get(), SubStmt
.get());
8011 template <typename Derived
>
8012 StmtResult TreeTransform
<Derived
>::TransformDefaultStmt(DefaultStmt
*S
) {
8013 // Transform the statement following the default case
8014 StmtResult SubStmt
=
8015 getDerived().TransformStmt(S
->getSubStmt());
8016 if (SubStmt
.isInvalid())
8019 // Default statements are always rebuilt
8020 return getDerived().RebuildDefaultStmt(S
->getDefaultLoc(), S
->getColonLoc(),
8024 template<typename Derived
>
8026 TreeTransform
<Derived
>::TransformLabelStmt(LabelStmt
*S
, StmtDiscardKind SDK
) {
8027 StmtResult SubStmt
= getDerived().TransformStmt(S
->getSubStmt(), SDK
);
8028 if (SubStmt
.isInvalid())
8031 Decl
*LD
= getDerived().TransformDecl(S
->getDecl()->getLocation(),
8036 // If we're transforming "in-place" (we're not creating new local
8037 // declarations), assume we're replacing the old label statement
8038 // and clear out the reference to it.
8039 if (LD
== S
->getDecl())
8040 S
->getDecl()->setStmt(nullptr);
8042 // FIXME: Pass the real colon location in.
8043 return getDerived().RebuildLabelStmt(S
->getIdentLoc(),
8044 cast
<LabelDecl
>(LD
), SourceLocation(),
8048 template <typename Derived
>
8049 const Attr
*TreeTransform
<Derived
>::TransformAttr(const Attr
*R
) {
8053 switch (R
->getKind()) {
8054 // Transform attributes by calling TransformXXXAttr.
8057 return getDerived().Transform##X##Attr(cast<X##Attr>(R));
8058 #include "clang/Basic/AttrList.inc"
8063 template <typename Derived
>
8064 const Attr
*TreeTransform
<Derived
>::TransformStmtAttr(const Stmt
*OrigS
,
8070 switch (R
->getKind()) {
8071 // Transform attributes by calling TransformStmtXXXAttr.
8074 return getDerived().TransformStmt##X##Attr(OrigS, InstS, cast<X##Attr>(R));
8075 #include "clang/Basic/AttrList.inc"
8077 return TransformAttr(R
);
8080 template <typename Derived
>
8082 TreeTransform
<Derived
>::TransformAttributedStmt(AttributedStmt
*S
,
8083 StmtDiscardKind SDK
) {
8084 StmtResult SubStmt
= getDerived().TransformStmt(S
->getSubStmt(), SDK
);
8085 if (SubStmt
.isInvalid())
8088 bool AttrsChanged
= false;
8089 SmallVector
<const Attr
*, 1> Attrs
;
8091 // Visit attributes and keep track if any are transformed.
8092 for (const auto *I
: S
->getAttrs()) {
8094 getDerived().TransformStmtAttr(S
->getSubStmt(), SubStmt
.get(), I
);
8095 AttrsChanged
|= (I
!= R
);
8100 if (SubStmt
.get() == S
->getSubStmt() && !AttrsChanged
)
8103 // If transforming the attributes failed for all of the attributes in the
8104 // statement, don't make an AttributedStmt without attributes.
8108 return getDerived().RebuildAttributedStmt(S
->getAttrLoc(), Attrs
,
8112 template<typename Derived
>
8114 TreeTransform
<Derived
>::TransformIfStmt(IfStmt
*S
) {
8115 // Transform the initialization statement
8116 StmtResult Init
= getDerived().TransformStmt(S
->getInit());
8117 if (Init
.isInvalid())
8120 Sema::ConditionResult Cond
;
8121 if (!S
->isConsteval()) {
8122 // Transform the condition
8123 Cond
= getDerived().TransformCondition(
8124 S
->getIfLoc(), S
->getConditionVariable(), S
->getCond(),
8125 S
->isConstexpr() ? Sema::ConditionKind::ConstexprIf
8126 : Sema::ConditionKind::Boolean
);
8127 if (Cond
.isInvalid())
8131 // If this is a constexpr if, determine which arm we should instantiate.
8132 std::optional
<bool> ConstexprConditionValue
;
8133 if (S
->isConstexpr())
8134 ConstexprConditionValue
= Cond
.getKnownValue();
8136 // Transform the "then" branch.
8138 if (!ConstexprConditionValue
|| *ConstexprConditionValue
) {
8139 EnterExpressionEvaluationContext
Ctx(
8140 getSema(), Sema::ExpressionEvaluationContext::ImmediateFunctionContext
,
8141 nullptr, Sema::ExpressionEvaluationContextRecord::EK_Other
,
8142 S
->isNonNegatedConsteval());
8144 Then
= getDerived().TransformStmt(S
->getThen());
8145 if (Then
.isInvalid())
8148 // Discarded branch is replaced with empty CompoundStmt so we can keep
8149 // proper source location for start and end of original branch, so
8150 // subsequent transformations like CoverageMapping work properly
8151 Then
= new (getSema().Context
)
8152 CompoundStmt(S
->getThen()->getBeginLoc(), S
->getThen()->getEndLoc());
8155 // Transform the "else" branch.
8157 if (!ConstexprConditionValue
|| !*ConstexprConditionValue
) {
8158 EnterExpressionEvaluationContext
Ctx(
8159 getSema(), Sema::ExpressionEvaluationContext::ImmediateFunctionContext
,
8160 nullptr, Sema::ExpressionEvaluationContextRecord::EK_Other
,
8161 S
->isNegatedConsteval());
8163 Else
= getDerived().TransformStmt(S
->getElse());
8164 if (Else
.isInvalid())
8166 } else if (S
->getElse() && ConstexprConditionValue
&&
8167 *ConstexprConditionValue
) {
8168 // Same thing here as with <then> branch, we are discarding it, we can't
8169 // replace it with NULL nor NullStmt as we need to keep for source location
8170 // range, for CoverageMapping
8171 Else
= new (getSema().Context
)
8172 CompoundStmt(S
->getElse()->getBeginLoc(), S
->getElse()->getEndLoc());
8175 if (!getDerived().AlwaysRebuild() &&
8176 Init
.get() == S
->getInit() &&
8177 Cond
.get() == std::make_pair(S
->getConditionVariable(), S
->getCond()) &&
8178 Then
.get() == S
->getThen() &&
8179 Else
.get() == S
->getElse())
8182 return getDerived().RebuildIfStmt(
8183 S
->getIfLoc(), S
->getStatementKind(), S
->getLParenLoc(), Cond
,
8184 S
->getRParenLoc(), Init
.get(), Then
.get(), S
->getElseLoc(), Else
.get());
8187 template<typename Derived
>
8189 TreeTransform
<Derived
>::TransformSwitchStmt(SwitchStmt
*S
) {
8190 // Transform the initialization statement
8191 StmtResult Init
= getDerived().TransformStmt(S
->getInit());
8192 if (Init
.isInvalid())
8195 // Transform the condition.
8196 Sema::ConditionResult Cond
= getDerived().TransformCondition(
8197 S
->getSwitchLoc(), S
->getConditionVariable(), S
->getCond(),
8198 Sema::ConditionKind::Switch
);
8199 if (Cond
.isInvalid())
8202 // Rebuild the switch statement.
8204 getDerived().RebuildSwitchStmtStart(S
->getSwitchLoc(), S
->getLParenLoc(),
8205 Init
.get(), Cond
, S
->getRParenLoc());
8206 if (Switch
.isInvalid())
8209 // Transform the body of the switch statement.
8210 StmtResult Body
= getDerived().TransformStmt(S
->getBody());
8211 if (Body
.isInvalid())
8214 // Complete the switch statement.
8215 return getDerived().RebuildSwitchStmtBody(S
->getSwitchLoc(), Switch
.get(),
8219 template<typename Derived
>
8221 TreeTransform
<Derived
>::TransformWhileStmt(WhileStmt
*S
) {
8222 // Transform the condition
8223 Sema::ConditionResult Cond
= getDerived().TransformCondition(
8224 S
->getWhileLoc(), S
->getConditionVariable(), S
->getCond(),
8225 Sema::ConditionKind::Boolean
);
8226 if (Cond
.isInvalid())
8229 // OpenACC Restricts a while-loop inside of certain construct/clause
8230 // combinations, so diagnose that here in OpenACC mode.
8231 SemaOpenACC::LoopInConstructRAII LCR
{SemaRef
.OpenACC()};
8232 SemaRef
.OpenACC().ActOnWhileStmt(S
->getBeginLoc());
8234 // Transform the body
8235 StmtResult Body
= getDerived().TransformStmt(S
->getBody());
8236 if (Body
.isInvalid())
8239 if (!getDerived().AlwaysRebuild() &&
8240 Cond
.get() == std::make_pair(S
->getConditionVariable(), S
->getCond()) &&
8241 Body
.get() == S
->getBody())
8244 return getDerived().RebuildWhileStmt(S
->getWhileLoc(), S
->getLParenLoc(),
8245 Cond
, S
->getRParenLoc(), Body
.get());
8248 template<typename Derived
>
8250 TreeTransform
<Derived
>::TransformDoStmt(DoStmt
*S
) {
8251 // OpenACC Restricts a do-loop inside of certain construct/clause
8252 // combinations, so diagnose that here in OpenACC mode.
8253 SemaOpenACC::LoopInConstructRAII LCR
{SemaRef
.OpenACC()};
8254 SemaRef
.OpenACC().ActOnDoStmt(S
->getBeginLoc());
8256 // Transform the body
8257 StmtResult Body
= getDerived().TransformStmt(S
->getBody());
8258 if (Body
.isInvalid())
8261 // Transform the condition
8262 ExprResult Cond
= getDerived().TransformExpr(S
->getCond());
8263 if (Cond
.isInvalid())
8266 if (!getDerived().AlwaysRebuild() &&
8267 Cond
.get() == S
->getCond() &&
8268 Body
.get() == S
->getBody())
8271 return getDerived().RebuildDoStmt(S
->getDoLoc(), Body
.get(), S
->getWhileLoc(),
8272 /*FIXME:*/S
->getWhileLoc(), Cond
.get(),
8276 template<typename Derived
>
8278 TreeTransform
<Derived
>::TransformForStmt(ForStmt
*S
) {
8279 if (getSema().getLangOpts().OpenMP
)
8280 getSema().OpenMP().startOpenMPLoop();
8282 // Transform the initialization statement
8283 StmtResult Init
= getDerived().TransformStmt(S
->getInit());
8284 if (Init
.isInvalid())
8287 // In OpenMP loop region loop control variable must be captured and be
8288 // private. Perform analysis of first part (if any).
8289 if (getSema().getLangOpts().OpenMP
&& Init
.isUsable())
8290 getSema().OpenMP().ActOnOpenMPLoopInitialization(S
->getForLoc(),
8293 // Transform the condition
8294 Sema::ConditionResult Cond
= getDerived().TransformCondition(
8295 S
->getForLoc(), S
->getConditionVariable(), S
->getCond(),
8296 Sema::ConditionKind::Boolean
);
8297 if (Cond
.isInvalid())
8300 // Transform the increment
8301 ExprResult Inc
= getDerived().TransformExpr(S
->getInc());
8302 if (Inc
.isInvalid())
8305 Sema::FullExprArg
FullInc(getSema().MakeFullDiscardedValueExpr(Inc
.get()));
8306 if (S
->getInc() && !FullInc
.get())
8309 // OpenACC Restricts a for-loop inside of certain construct/clause
8310 // combinations, so diagnose that here in OpenACC mode.
8311 SemaOpenACC::LoopInConstructRAII LCR
{SemaRef
.OpenACC()};
8312 SemaRef
.OpenACC().ActOnForStmtBegin(
8313 S
->getBeginLoc(), S
->getInit(), Init
.get(), S
->getCond(),
8314 Cond
.get().second
, S
->getInc(), Inc
.get());
8316 // Transform the body
8317 StmtResult Body
= getDerived().TransformStmt(S
->getBody());
8318 if (Body
.isInvalid())
8321 SemaRef
.OpenACC().ActOnForStmtEnd(S
->getBeginLoc(), Body
);
8323 if (!getDerived().AlwaysRebuild() &&
8324 Init
.get() == S
->getInit() &&
8325 Cond
.get() == std::make_pair(S
->getConditionVariable(), S
->getCond()) &&
8326 Inc
.get() == S
->getInc() &&
8327 Body
.get() == S
->getBody())
8330 return getDerived().RebuildForStmt(S
->getForLoc(), S
->getLParenLoc(),
8331 Init
.get(), Cond
, FullInc
,
8332 S
->getRParenLoc(), Body
.get());
8335 template<typename Derived
>
8337 TreeTransform
<Derived
>::TransformGotoStmt(GotoStmt
*S
) {
8338 Decl
*LD
= getDerived().TransformDecl(S
->getLabel()->getLocation(),
8343 // Goto statements must always be rebuilt, to resolve the label.
8344 return getDerived().RebuildGotoStmt(S
->getGotoLoc(), S
->getLabelLoc(),
8345 cast
<LabelDecl
>(LD
));
8348 template<typename Derived
>
8350 TreeTransform
<Derived
>::TransformIndirectGotoStmt(IndirectGotoStmt
*S
) {
8351 ExprResult Target
= getDerived().TransformExpr(S
->getTarget());
8352 if (Target
.isInvalid())
8354 Target
= SemaRef
.MaybeCreateExprWithCleanups(Target
.get());
8356 if (!getDerived().AlwaysRebuild() &&
8357 Target
.get() == S
->getTarget())
8360 return getDerived().RebuildIndirectGotoStmt(S
->getGotoLoc(), S
->getStarLoc(),
8364 template<typename Derived
>
8366 TreeTransform
<Derived
>::TransformContinueStmt(ContinueStmt
*S
) {
8370 template<typename Derived
>
8372 TreeTransform
<Derived
>::TransformBreakStmt(BreakStmt
*S
) {
8376 template<typename Derived
>
8378 TreeTransform
<Derived
>::TransformReturnStmt(ReturnStmt
*S
) {
8379 ExprResult Result
= getDerived().TransformInitializer(S
->getRetValue(),
8380 /*NotCopyInit*/false);
8381 if (Result
.isInvalid())
8384 // FIXME: We always rebuild the return statement because there is no way
8385 // to tell whether the return type of the function has changed.
8386 return getDerived().RebuildReturnStmt(S
->getReturnLoc(), Result
.get());
8389 template<typename Derived
>
8391 TreeTransform
<Derived
>::TransformDeclStmt(DeclStmt
*S
) {
8392 bool DeclChanged
= false;
8393 SmallVector
<Decl
*, 4> Decls
;
8394 LambdaScopeInfo
*LSI
= getSema().getCurLambda();
8395 for (auto *D
: S
->decls()) {
8396 Decl
*Transformed
= getDerived().TransformDefinition(D
->getLocation(), D
);
8400 if (Transformed
!= D
)
8404 if (auto *TD
= dyn_cast
<TypeDecl
>(Transformed
))
8405 LSI
->ContainsUnexpandedParameterPack
|=
8408 .getTypeDeclType(TD
)
8410 ->containsUnexpandedParameterPack();
8412 if (auto *VD
= dyn_cast
<VarDecl
>(Transformed
))
8413 LSI
->ContainsUnexpandedParameterPack
|=
8414 VD
->getType()->containsUnexpandedParameterPack();
8417 Decls
.push_back(Transformed
);
8420 if (!getDerived().AlwaysRebuild() && !DeclChanged
)
8423 return getDerived().RebuildDeclStmt(Decls
, S
->getBeginLoc(), S
->getEndLoc());
8426 template<typename Derived
>
8428 TreeTransform
<Derived
>::TransformGCCAsmStmt(GCCAsmStmt
*S
) {
8430 SmallVector
<Expr
*, 8> Constraints
;
8431 SmallVector
<Expr
*, 8> Exprs
;
8432 SmallVector
<IdentifierInfo
*, 4> Names
;
8434 ExprResult AsmString
;
8435 SmallVector
<Expr
*, 8> Clobbers
;
8437 bool ExprsChanged
= false;
8439 // Go through the outputs.
8440 for (unsigned I
= 0, E
= S
->getNumOutputs(); I
!= E
; ++I
) {
8441 Names
.push_back(S
->getOutputIdentifier(I
));
8443 // No need to transform the constraint literal.
8444 Constraints
.push_back(S
->getOutputConstraintLiteral(I
));
8446 // Transform the output expr.
8447 Expr
*OutputExpr
= S
->getOutputExpr(I
);
8448 ExprResult Result
= getDerived().TransformExpr(OutputExpr
);
8449 if (Result
.isInvalid())
8452 ExprsChanged
|= Result
.get() != OutputExpr
;
8454 Exprs
.push_back(Result
.get());
8457 // Go through the inputs.
8458 for (unsigned I
= 0, E
= S
->getNumInputs(); I
!= E
; ++I
) {
8459 Names
.push_back(S
->getInputIdentifier(I
));
8461 // No need to transform the constraint literal.
8462 Constraints
.push_back(S
->getInputConstraintLiteral(I
));
8464 // Transform the input expr.
8465 Expr
*InputExpr
= S
->getInputExpr(I
);
8466 ExprResult Result
= getDerived().TransformExpr(InputExpr
);
8467 if (Result
.isInvalid())
8470 ExprsChanged
|= Result
.get() != InputExpr
;
8472 Exprs
.push_back(Result
.get());
8475 // Go through the Labels.
8476 for (unsigned I
= 0, E
= S
->getNumLabels(); I
!= E
; ++I
) {
8477 Names
.push_back(S
->getLabelIdentifier(I
));
8479 ExprResult Result
= getDerived().TransformExpr(S
->getLabelExpr(I
));
8480 if (Result
.isInvalid())
8482 ExprsChanged
|= Result
.get() != S
->getLabelExpr(I
);
8483 Exprs
.push_back(Result
.get());
8485 if (!getDerived().AlwaysRebuild() && !ExprsChanged
)
8488 // Go through the clobbers.
8489 for (unsigned I
= 0, E
= S
->getNumClobbers(); I
!= E
; ++I
)
8490 Clobbers
.push_back(S
->getClobberStringLiteral(I
));
8492 // No need to transform the asm string literal.
8493 AsmString
= S
->getAsmString();
8494 return getDerived().RebuildGCCAsmStmt(S
->getAsmLoc(), S
->isSimple(),
8495 S
->isVolatile(), S
->getNumOutputs(),
8496 S
->getNumInputs(), Names
.data(),
8497 Constraints
, Exprs
, AsmString
.get(),
8498 Clobbers
, S
->getNumLabels(),
8502 template<typename Derived
>
8504 TreeTransform
<Derived
>::TransformMSAsmStmt(MSAsmStmt
*S
) {
8505 ArrayRef
<Token
> AsmToks
= llvm::ArrayRef(S
->getAsmToks(), S
->getNumAsmToks());
8507 bool HadError
= false, HadChange
= false;
8509 ArrayRef
<Expr
*> SrcExprs
= S
->getAllExprs();
8510 SmallVector
<Expr
*, 8> TransformedExprs
;
8511 TransformedExprs
.reserve(SrcExprs
.size());
8512 for (unsigned i
= 0, e
= SrcExprs
.size(); i
!= e
; ++i
) {
8513 ExprResult Result
= getDerived().TransformExpr(SrcExprs
[i
]);
8514 if (!Result
.isUsable()) {
8517 HadChange
|= (Result
.get() != SrcExprs
[i
]);
8518 TransformedExprs
.push_back(Result
.get());
8522 if (HadError
) return StmtError();
8523 if (!HadChange
&& !getDerived().AlwaysRebuild())
8526 return getDerived().RebuildMSAsmStmt(S
->getAsmLoc(), S
->getLBraceLoc(),
8527 AsmToks
, S
->getAsmString(),
8528 S
->getNumOutputs(), S
->getNumInputs(),
8529 S
->getAllConstraints(), S
->getClobbers(),
8530 TransformedExprs
, S
->getEndLoc());
8534 template<typename Derived
>
8536 TreeTransform
<Derived
>::TransformCoroutineBodyStmt(CoroutineBodyStmt
*S
) {
8537 auto *ScopeInfo
= SemaRef
.getCurFunction();
8538 auto *FD
= cast
<FunctionDecl
>(SemaRef
.CurContext
);
8539 assert(FD
&& ScopeInfo
&& !ScopeInfo
->CoroutinePromise
&&
8540 ScopeInfo
->NeedsCoroutineSuspends
&&
8541 ScopeInfo
->CoroutineSuspends
.first
== nullptr &&
8542 ScopeInfo
->CoroutineSuspends
.second
== nullptr &&
8543 "expected clean scope info");
8545 // Set that we have (possibly-invalid) suspend points before we do anything
8547 ScopeInfo
->setNeedsCoroutineSuspends(false);
8549 // We re-build the coroutine promise object (and the coroutine parameters its
8550 // type and constructor depend on) based on the types used in our current
8551 // function. We must do so, and set it on the current FunctionScopeInfo,
8552 // before attempting to transform the other parts of the coroutine body
8553 // statement, such as the implicit suspend statements (because those
8554 // statements reference the FunctionScopeInfo::CoroutinePromise).
8555 if (!SemaRef
.buildCoroutineParameterMoves(FD
->getLocation()))
8557 auto *Promise
= SemaRef
.buildCoroutinePromise(FD
->getLocation());
8560 getDerived().transformedLocalDecl(S
->getPromiseDecl(), {Promise
});
8561 ScopeInfo
->CoroutinePromise
= Promise
;
8563 // Transform the implicit coroutine statements constructed using dependent
8564 // types during the previous parse: initial and final suspensions, the return
8565 // object, and others. We also transform the coroutine function's body.
8566 StmtResult InitSuspend
= getDerived().TransformStmt(S
->getInitSuspendStmt());
8567 if (InitSuspend
.isInvalid())
8569 StmtResult FinalSuspend
=
8570 getDerived().TransformStmt(S
->getFinalSuspendStmt());
8571 if (FinalSuspend
.isInvalid() ||
8572 !SemaRef
.checkFinalSuspendNoThrow(FinalSuspend
.get()))
8574 ScopeInfo
->setCoroutineSuspends(InitSuspend
.get(), FinalSuspend
.get());
8575 assert(isa
<Expr
>(InitSuspend
.get()) && isa
<Expr
>(FinalSuspend
.get()));
8577 StmtResult BodyRes
= getDerived().TransformStmt(S
->getBody());
8578 if (BodyRes
.isInvalid())
8581 CoroutineStmtBuilder
Builder(SemaRef
, *FD
, *ScopeInfo
, BodyRes
.get());
8582 if (Builder
.isInvalid())
8585 Expr
*ReturnObject
= S
->getReturnValueInit();
8586 assert(ReturnObject
&& "the return object is expected to be valid");
8587 ExprResult Res
= getDerived().TransformInitializer(ReturnObject
,
8588 /*NoCopyInit*/ false);
8589 if (Res
.isInvalid())
8591 Builder
.ReturnValue
= Res
.get();
8593 // If during the previous parse the coroutine still had a dependent promise
8594 // statement, we may need to build some implicit coroutine statements
8595 // (such as exception and fallthrough handlers) for the first time.
8596 if (S
->hasDependentPromiseType()) {
8597 // We can only build these statements, however, if the current promise type
8598 // is not dependent.
8599 if (!Promise
->getType()->isDependentType()) {
8600 assert(!S
->getFallthroughHandler() && !S
->getExceptionHandler() &&
8601 !S
->getReturnStmtOnAllocFailure() && !S
->getDeallocate() &&
8602 "these nodes should not have been built yet");
8603 if (!Builder
.buildDependentStatements())
8607 if (auto *OnFallthrough
= S
->getFallthroughHandler()) {
8608 StmtResult Res
= getDerived().TransformStmt(OnFallthrough
);
8609 if (Res
.isInvalid())
8611 Builder
.OnFallthrough
= Res
.get();
8614 if (auto *OnException
= S
->getExceptionHandler()) {
8615 StmtResult Res
= getDerived().TransformStmt(OnException
);
8616 if (Res
.isInvalid())
8618 Builder
.OnException
= Res
.get();
8621 if (auto *OnAllocFailure
= S
->getReturnStmtOnAllocFailure()) {
8622 StmtResult Res
= getDerived().TransformStmt(OnAllocFailure
);
8623 if (Res
.isInvalid())
8625 Builder
.ReturnStmtOnAllocFailure
= Res
.get();
8628 // Transform any additional statements we may have already built
8629 assert(S
->getAllocate() && S
->getDeallocate() &&
8630 "allocation and deallocation calls must already be built");
8631 ExprResult AllocRes
= getDerived().TransformExpr(S
->getAllocate());
8632 if (AllocRes
.isInvalid())
8634 Builder
.Allocate
= AllocRes
.get();
8636 ExprResult DeallocRes
= getDerived().TransformExpr(S
->getDeallocate());
8637 if (DeallocRes
.isInvalid())
8639 Builder
.Deallocate
= DeallocRes
.get();
8641 if (auto *ResultDecl
= S
->getResultDecl()) {
8642 StmtResult Res
= getDerived().TransformStmt(ResultDecl
);
8643 if (Res
.isInvalid())
8645 Builder
.ResultDecl
= Res
.get();
8648 if (auto *ReturnStmt
= S
->getReturnStmt()) {
8649 StmtResult Res
= getDerived().TransformStmt(ReturnStmt
);
8650 if (Res
.isInvalid())
8652 Builder
.ReturnStmt
= Res
.get();
8656 return getDerived().RebuildCoroutineBodyStmt(Builder
);
8659 template<typename Derived
>
8661 TreeTransform
<Derived
>::TransformCoreturnStmt(CoreturnStmt
*S
) {
8662 ExprResult Result
= getDerived().TransformInitializer(S
->getOperand(),
8663 /*NotCopyInit*/false);
8664 if (Result
.isInvalid())
8667 // Always rebuild; we don't know if this needs to be injected into a new
8668 // context or if the promise type has changed.
8669 return getDerived().RebuildCoreturnStmt(S
->getKeywordLoc(), Result
.get(),
8673 template <typename Derived
>
8674 ExprResult TreeTransform
<Derived
>::TransformCoawaitExpr(CoawaitExpr
*E
) {
8675 ExprResult Operand
= getDerived().TransformInitializer(E
->getOperand(),
8676 /*NotCopyInit*/ false);
8677 if (Operand
.isInvalid())
8680 // Rebuild the common-expr from the operand rather than transforming it
8683 // FIXME: getCurScope() should not be used during template instantiation.
8684 // We should pick up the set of unqualified lookup results for operator
8685 // co_await during the initial parse.
8686 ExprResult Lookup
= getSema().BuildOperatorCoawaitLookupExpr(
8687 getSema().getCurScope(), E
->getKeywordLoc());
8689 // Always rebuild; we don't know if this needs to be injected into a new
8690 // context or if the promise type has changed.
8691 return getDerived().RebuildCoawaitExpr(
8692 E
->getKeywordLoc(), Operand
.get(),
8693 cast
<UnresolvedLookupExpr
>(Lookup
.get()), E
->isImplicit());
8696 template <typename Derived
>
8698 TreeTransform
<Derived
>::TransformDependentCoawaitExpr(DependentCoawaitExpr
*E
) {
8699 ExprResult OperandResult
= getDerived().TransformInitializer(E
->getOperand(),
8700 /*NotCopyInit*/ false);
8701 if (OperandResult
.isInvalid())
8704 ExprResult LookupResult
= getDerived().TransformUnresolvedLookupExpr(
8705 E
->getOperatorCoawaitLookup());
8707 if (LookupResult
.isInvalid())
8710 // Always rebuild; we don't know if this needs to be injected into a new
8711 // context or if the promise type has changed.
8712 return getDerived().RebuildDependentCoawaitExpr(
8713 E
->getKeywordLoc(), OperandResult
.get(),
8714 cast
<UnresolvedLookupExpr
>(LookupResult
.get()));
8717 template<typename Derived
>
8719 TreeTransform
<Derived
>::TransformCoyieldExpr(CoyieldExpr
*E
) {
8720 ExprResult Result
= getDerived().TransformInitializer(E
->getOperand(),
8721 /*NotCopyInit*/false);
8722 if (Result
.isInvalid())
8725 // Always rebuild; we don't know if this needs to be injected into a new
8726 // context or if the promise type has changed.
8727 return getDerived().RebuildCoyieldExpr(E
->getKeywordLoc(), Result
.get());
8730 // Objective-C Statements.
8732 template<typename Derived
>
8734 TreeTransform
<Derived
>::TransformObjCAtTryStmt(ObjCAtTryStmt
*S
) {
8735 // Transform the body of the @try.
8736 StmtResult TryBody
= getDerived().TransformStmt(S
->getTryBody());
8737 if (TryBody
.isInvalid())
8740 // Transform the @catch statements (if present).
8741 bool AnyCatchChanged
= false;
8742 SmallVector
<Stmt
*, 8> CatchStmts
;
8743 for (unsigned I
= 0, N
= S
->getNumCatchStmts(); I
!= N
; ++I
) {
8744 StmtResult Catch
= getDerived().TransformStmt(S
->getCatchStmt(I
));
8745 if (Catch
.isInvalid())
8747 if (Catch
.get() != S
->getCatchStmt(I
))
8748 AnyCatchChanged
= true;
8749 CatchStmts
.push_back(Catch
.get());
8752 // Transform the @finally statement (if present).
8754 if (S
->getFinallyStmt()) {
8755 Finally
= getDerived().TransformStmt(S
->getFinallyStmt());
8756 if (Finally
.isInvalid())
8760 // If nothing changed, just retain this statement.
8761 if (!getDerived().AlwaysRebuild() &&
8762 TryBody
.get() == S
->getTryBody() &&
8764 Finally
.get() == S
->getFinallyStmt())
8767 // Build a new statement.
8768 return getDerived().RebuildObjCAtTryStmt(S
->getAtTryLoc(), TryBody
.get(),
8769 CatchStmts
, Finally
.get());
8772 template<typename Derived
>
8774 TreeTransform
<Derived
>::TransformObjCAtCatchStmt(ObjCAtCatchStmt
*S
) {
8775 // Transform the @catch parameter, if there is one.
8776 VarDecl
*Var
= nullptr;
8777 if (VarDecl
*FromVar
= S
->getCatchParamDecl()) {
8778 TypeSourceInfo
*TSInfo
= nullptr;
8779 if (FromVar
->getTypeSourceInfo()) {
8780 TSInfo
= getDerived().TransformType(FromVar
->getTypeSourceInfo());
8787 T
= TSInfo
->getType();
8789 T
= getDerived().TransformType(FromVar
->getType());
8794 Var
= getDerived().RebuildObjCExceptionDecl(FromVar
, TSInfo
, T
);
8799 StmtResult Body
= getDerived().TransformStmt(S
->getCatchBody());
8800 if (Body
.isInvalid())
8803 return getDerived().RebuildObjCAtCatchStmt(S
->getAtCatchLoc(),
8808 template<typename Derived
>
8810 TreeTransform
<Derived
>::TransformObjCAtFinallyStmt(ObjCAtFinallyStmt
*S
) {
8811 // Transform the body.
8812 StmtResult Body
= getDerived().TransformStmt(S
->getFinallyBody());
8813 if (Body
.isInvalid())
8816 // If nothing changed, just retain this statement.
8817 if (!getDerived().AlwaysRebuild() &&
8818 Body
.get() == S
->getFinallyBody())
8821 // Build a new statement.
8822 return getDerived().RebuildObjCAtFinallyStmt(S
->getAtFinallyLoc(),
8826 template<typename Derived
>
8828 TreeTransform
<Derived
>::TransformObjCAtThrowStmt(ObjCAtThrowStmt
*S
) {
8830 if (S
->getThrowExpr()) {
8831 Operand
= getDerived().TransformExpr(S
->getThrowExpr());
8832 if (Operand
.isInvalid())
8836 if (!getDerived().AlwaysRebuild() &&
8837 Operand
.get() == S
->getThrowExpr())
8840 return getDerived().RebuildObjCAtThrowStmt(S
->getThrowLoc(), Operand
.get());
8843 template<typename Derived
>
8845 TreeTransform
<Derived
>::TransformObjCAtSynchronizedStmt(
8846 ObjCAtSynchronizedStmt
*S
) {
8847 // Transform the object we are locking.
8848 ExprResult Object
= getDerived().TransformExpr(S
->getSynchExpr());
8849 if (Object
.isInvalid())
8852 getDerived().RebuildObjCAtSynchronizedOperand(S
->getAtSynchronizedLoc(),
8854 if (Object
.isInvalid())
8857 // Transform the body.
8858 StmtResult Body
= getDerived().TransformStmt(S
->getSynchBody());
8859 if (Body
.isInvalid())
8862 // If nothing change, just retain the current statement.
8863 if (!getDerived().AlwaysRebuild() &&
8864 Object
.get() == S
->getSynchExpr() &&
8865 Body
.get() == S
->getSynchBody())
8868 // Build a new statement.
8869 return getDerived().RebuildObjCAtSynchronizedStmt(S
->getAtSynchronizedLoc(),
8870 Object
.get(), Body
.get());
8873 template<typename Derived
>
8875 TreeTransform
<Derived
>::TransformObjCAutoreleasePoolStmt(
8876 ObjCAutoreleasePoolStmt
*S
) {
8877 // Transform the body.
8878 StmtResult Body
= getDerived().TransformStmt(S
->getSubStmt());
8879 if (Body
.isInvalid())
8882 // If nothing changed, just retain this statement.
8883 if (!getDerived().AlwaysRebuild() &&
8884 Body
.get() == S
->getSubStmt())
8887 // Build a new statement.
8888 return getDerived().RebuildObjCAutoreleasePoolStmt(
8889 S
->getAtLoc(), Body
.get());
8892 template<typename Derived
>
8894 TreeTransform
<Derived
>::TransformObjCForCollectionStmt(
8895 ObjCForCollectionStmt
*S
) {
8896 // Transform the element statement.
8897 StmtResult Element
=
8898 getDerived().TransformStmt(S
->getElement(), SDK_NotDiscarded
);
8899 if (Element
.isInvalid())
8902 // Transform the collection expression.
8903 ExprResult Collection
= getDerived().TransformExpr(S
->getCollection());
8904 if (Collection
.isInvalid())
8907 // Transform the body.
8908 StmtResult Body
= getDerived().TransformStmt(S
->getBody());
8909 if (Body
.isInvalid())
8912 // If nothing changed, just retain this statement.
8913 if (!getDerived().AlwaysRebuild() &&
8914 Element
.get() == S
->getElement() &&
8915 Collection
.get() == S
->getCollection() &&
8916 Body
.get() == S
->getBody())
8919 // Build a new statement.
8920 return getDerived().RebuildObjCForCollectionStmt(S
->getForLoc(),
8927 template <typename Derived
>
8928 StmtResult TreeTransform
<Derived
>::TransformCXXCatchStmt(CXXCatchStmt
*S
) {
8929 // Transform the exception declaration, if any.
8930 VarDecl
*Var
= nullptr;
8931 if (VarDecl
*ExceptionDecl
= S
->getExceptionDecl()) {
8933 getDerived().TransformType(ExceptionDecl
->getTypeSourceInfo());
8937 Var
= getDerived().RebuildExceptionDecl(
8938 ExceptionDecl
, T
, ExceptionDecl
->getInnerLocStart(),
8939 ExceptionDecl
->getLocation(), ExceptionDecl
->getIdentifier());
8940 if (!Var
|| Var
->isInvalidDecl())
8944 // Transform the actual exception handler.
8945 StmtResult Handler
= getDerived().TransformStmt(S
->getHandlerBlock());
8946 if (Handler
.isInvalid())
8949 if (!getDerived().AlwaysRebuild() && !Var
&&
8950 Handler
.get() == S
->getHandlerBlock())
8953 return getDerived().RebuildCXXCatchStmt(S
->getCatchLoc(), Var
, Handler
.get());
8956 template <typename Derived
>
8957 StmtResult TreeTransform
<Derived
>::TransformCXXTryStmt(CXXTryStmt
*S
) {
8958 // Transform the try block itself.
8959 StmtResult TryBlock
= getDerived().TransformCompoundStmt(S
->getTryBlock());
8960 if (TryBlock
.isInvalid())
8963 // Transform the handlers.
8964 bool HandlerChanged
= false;
8965 SmallVector
<Stmt
*, 8> Handlers
;
8966 for (unsigned I
= 0, N
= S
->getNumHandlers(); I
!= N
; ++I
) {
8967 StmtResult Handler
= getDerived().TransformCXXCatchStmt(S
->getHandler(I
));
8968 if (Handler
.isInvalid())
8971 HandlerChanged
= HandlerChanged
|| Handler
.get() != S
->getHandler(I
);
8972 Handlers
.push_back(Handler
.getAs
<Stmt
>());
8975 if (!getDerived().AlwaysRebuild() && TryBlock
.get() == S
->getTryBlock() &&
8979 return getDerived().RebuildCXXTryStmt(S
->getTryLoc(), TryBlock
.get(),
8983 template<typename Derived
>
8985 TreeTransform
<Derived
>::TransformCXXForRangeStmt(CXXForRangeStmt
*S
) {
8986 EnterExpressionEvaluationContext
ForRangeInitContext(
8987 getSema(), Sema::ExpressionEvaluationContext::PotentiallyEvaluated
,
8988 /*LambdaContextDecl=*/nullptr,
8989 Sema::ExpressionEvaluationContextRecord::EK_Other
,
8990 getSema().getLangOpts().CPlusPlus23
);
8992 // P2718R0 - Lifetime extension in range-based for loops.
8993 if (getSema().getLangOpts().CPlusPlus23
) {
8994 auto &LastRecord
= getSema().currentEvaluationContext();
8995 LastRecord
.InLifetimeExtendingContext
= true;
8996 LastRecord
.RebuildDefaultArgOrDefaultInit
= true;
8999 S
->getInit() ? getDerived().TransformStmt(S
->getInit()) : StmtResult();
9000 if (Init
.isInvalid())
9003 StmtResult Range
= getDerived().TransformStmt(S
->getRangeStmt());
9004 if (Range
.isInvalid())
9007 // Before c++23, ForRangeLifetimeExtendTemps should be empty.
9008 assert(getSema().getLangOpts().CPlusPlus23
||
9009 getSema().ExprEvalContexts
.back().ForRangeLifetimeExtendTemps
.empty());
9010 auto ForRangeLifetimeExtendTemps
=
9011 getSema().ExprEvalContexts
.back().ForRangeLifetimeExtendTemps
;
9013 StmtResult Begin
= getDerived().TransformStmt(S
->getBeginStmt());
9014 if (Begin
.isInvalid())
9016 StmtResult End
= getDerived().TransformStmt(S
->getEndStmt());
9017 if (End
.isInvalid())
9020 ExprResult Cond
= getDerived().TransformExpr(S
->getCond());
9021 if (Cond
.isInvalid())
9024 Cond
= SemaRef
.CheckBooleanCondition(S
->getColonLoc(), Cond
.get());
9025 if (Cond
.isInvalid())
9028 Cond
= SemaRef
.MaybeCreateExprWithCleanups(Cond
.get());
9030 ExprResult Inc
= getDerived().TransformExpr(S
->getInc());
9031 if (Inc
.isInvalid())
9034 Inc
= SemaRef
.MaybeCreateExprWithCleanups(Inc
.get());
9036 StmtResult LoopVar
= getDerived().TransformStmt(S
->getLoopVarStmt());
9037 if (LoopVar
.isInvalid())
9040 StmtResult NewStmt
= S
;
9041 if (getDerived().AlwaysRebuild() ||
9042 Init
.get() != S
->getInit() ||
9043 Range
.get() != S
->getRangeStmt() ||
9044 Begin
.get() != S
->getBeginStmt() ||
9045 End
.get() != S
->getEndStmt() ||
9046 Cond
.get() != S
->getCond() ||
9047 Inc
.get() != S
->getInc() ||
9048 LoopVar
.get() != S
->getLoopVarStmt()) {
9049 NewStmt
= getDerived().RebuildCXXForRangeStmt(
9050 S
->getForLoc(), S
->getCoawaitLoc(), Init
.get(), S
->getColonLoc(),
9051 Range
.get(), Begin
.get(), End
.get(), Cond
.get(), Inc
.get(),
9052 LoopVar
.get(), S
->getRParenLoc(), ForRangeLifetimeExtendTemps
);
9053 if (NewStmt
.isInvalid() && LoopVar
.get() != S
->getLoopVarStmt()) {
9054 // Might not have attached any initializer to the loop variable.
9055 getSema().ActOnInitializerError(
9056 cast
<DeclStmt
>(LoopVar
.get())->getSingleDecl());
9061 // OpenACC Restricts a while-loop inside of certain construct/clause
9062 // combinations, so diagnose that here in OpenACC mode.
9063 SemaOpenACC::LoopInConstructRAII LCR
{SemaRef
.OpenACC()};
9064 SemaRef
.OpenACC().ActOnRangeForStmtBegin(S
->getBeginLoc(), S
, NewStmt
.get());
9066 StmtResult Body
= getDerived().TransformStmt(S
->getBody());
9067 if (Body
.isInvalid())
9070 SemaRef
.OpenACC().ActOnForStmtEnd(S
->getBeginLoc(), Body
);
9072 // Body has changed but we didn't rebuild the for-range statement. Rebuild
9073 // it now so we have a new statement to attach the body to.
9074 if (Body
.get() != S
->getBody() && NewStmt
.get() == S
) {
9075 NewStmt
= getDerived().RebuildCXXForRangeStmt(
9076 S
->getForLoc(), S
->getCoawaitLoc(), Init
.get(), S
->getColonLoc(),
9077 Range
.get(), Begin
.get(), End
.get(), Cond
.get(), Inc
.get(),
9078 LoopVar
.get(), S
->getRParenLoc(), ForRangeLifetimeExtendTemps
);
9079 if (NewStmt
.isInvalid())
9083 if (NewStmt
.get() == S
)
9086 return FinishCXXForRangeStmt(NewStmt
.get(), Body
.get());
9089 template<typename Derived
>
9091 TreeTransform
<Derived
>::TransformMSDependentExistsStmt(
9092 MSDependentExistsStmt
*S
) {
9093 // Transform the nested-name-specifier, if any.
9094 NestedNameSpecifierLoc QualifierLoc
;
9095 if (S
->getQualifierLoc()) {
9097 = getDerived().TransformNestedNameSpecifierLoc(S
->getQualifierLoc());
9102 // Transform the declaration name.
9103 DeclarationNameInfo NameInfo
= S
->getNameInfo();
9104 if (NameInfo
.getName()) {
9105 NameInfo
= getDerived().TransformDeclarationNameInfo(NameInfo
);
9106 if (!NameInfo
.getName())
9110 // Check whether anything changed.
9111 if (!getDerived().AlwaysRebuild() &&
9112 QualifierLoc
== S
->getQualifierLoc() &&
9113 NameInfo
.getName() == S
->getNameInfo().getName())
9116 // Determine whether this name exists, if we can.
9118 SS
.Adopt(QualifierLoc
);
9119 bool Dependent
= false;
9120 switch (getSema().CheckMicrosoftIfExistsSymbol(/*S=*/nullptr, SS
, NameInfo
)) {
9121 case Sema::IER_Exists
:
9122 if (S
->isIfExists())
9125 return new (getSema().Context
) NullStmt(S
->getKeywordLoc());
9127 case Sema::IER_DoesNotExist
:
9128 if (S
->isIfNotExists())
9131 return new (getSema().Context
) NullStmt(S
->getKeywordLoc());
9133 case Sema::IER_Dependent
:
9137 case Sema::IER_Error
:
9141 // We need to continue with the instantiation, so do so now.
9142 StmtResult SubStmt
= getDerived().TransformCompoundStmt(S
->getSubStmt());
9143 if (SubStmt
.isInvalid())
9146 // If we have resolved the name, just transform to the substatement.
9150 // The name is still dependent, so build a dependent expression again.
9151 return getDerived().RebuildMSDependentExistsStmt(S
->getKeywordLoc(),
9158 template<typename Derived
>
9160 TreeTransform
<Derived
>::TransformMSPropertyRefExpr(MSPropertyRefExpr
*E
) {
9161 NestedNameSpecifierLoc QualifierLoc
;
9162 if (E
->getQualifierLoc()) {
9164 = getDerived().TransformNestedNameSpecifierLoc(E
->getQualifierLoc());
9169 MSPropertyDecl
*PD
= cast_or_null
<MSPropertyDecl
>(
9170 getDerived().TransformDecl(E
->getMemberLoc(), E
->getPropertyDecl()));
9174 ExprResult Base
= getDerived().TransformExpr(E
->getBaseExpr());
9175 if (Base
.isInvalid())
9178 return new (SemaRef
.getASTContext())
9179 MSPropertyRefExpr(Base
.get(), PD
, E
->isArrow(),
9180 SemaRef
.getASTContext().PseudoObjectTy
, VK_LValue
,
9181 QualifierLoc
, E
->getMemberLoc());
9184 template <typename Derived
>
9185 ExprResult TreeTransform
<Derived
>::TransformMSPropertySubscriptExpr(
9186 MSPropertySubscriptExpr
*E
) {
9187 auto BaseRes
= getDerived().TransformExpr(E
->getBase());
9188 if (BaseRes
.isInvalid())
9190 auto IdxRes
= getDerived().TransformExpr(E
->getIdx());
9191 if (IdxRes
.isInvalid())
9194 if (!getDerived().AlwaysRebuild() &&
9195 BaseRes
.get() == E
->getBase() &&
9196 IdxRes
.get() == E
->getIdx())
9199 return getDerived().RebuildArraySubscriptExpr(
9200 BaseRes
.get(), SourceLocation(), IdxRes
.get(), E
->getRBracketLoc());
9203 template <typename Derived
>
9204 StmtResult TreeTransform
<Derived
>::TransformSEHTryStmt(SEHTryStmt
*S
) {
9205 StmtResult TryBlock
= getDerived().TransformCompoundStmt(S
->getTryBlock());
9206 if (TryBlock
.isInvalid())
9209 StmtResult Handler
= getDerived().TransformSEHHandler(S
->getHandler());
9210 if (Handler
.isInvalid())
9213 if (!getDerived().AlwaysRebuild() && TryBlock
.get() == S
->getTryBlock() &&
9214 Handler
.get() == S
->getHandler())
9217 return getDerived().RebuildSEHTryStmt(S
->getIsCXXTry(), S
->getTryLoc(),
9218 TryBlock
.get(), Handler
.get());
9221 template <typename Derived
>
9222 StmtResult TreeTransform
<Derived
>::TransformSEHFinallyStmt(SEHFinallyStmt
*S
) {
9223 StmtResult Block
= getDerived().TransformCompoundStmt(S
->getBlock());
9224 if (Block
.isInvalid())
9227 return getDerived().RebuildSEHFinallyStmt(S
->getFinallyLoc(), Block
.get());
9230 template <typename Derived
>
9231 StmtResult TreeTransform
<Derived
>::TransformSEHExceptStmt(SEHExceptStmt
*S
) {
9232 ExprResult FilterExpr
= getDerived().TransformExpr(S
->getFilterExpr());
9233 if (FilterExpr
.isInvalid())
9236 StmtResult Block
= getDerived().TransformCompoundStmt(S
->getBlock());
9237 if (Block
.isInvalid())
9240 return getDerived().RebuildSEHExceptStmt(S
->getExceptLoc(), FilterExpr
.get(),
9244 template <typename Derived
>
9245 StmtResult TreeTransform
<Derived
>::TransformSEHHandler(Stmt
*Handler
) {
9246 if (isa
<SEHFinallyStmt
>(Handler
))
9247 return getDerived().TransformSEHFinallyStmt(cast
<SEHFinallyStmt
>(Handler
));
9249 return getDerived().TransformSEHExceptStmt(cast
<SEHExceptStmt
>(Handler
));
9252 template<typename Derived
>
9254 TreeTransform
<Derived
>::TransformSEHLeaveStmt(SEHLeaveStmt
*S
) {
9258 //===----------------------------------------------------------------------===//
9259 // OpenMP directive transformation
9260 //===----------------------------------------------------------------------===//
9262 template <typename Derived
>
9264 TreeTransform
<Derived
>::TransformOMPCanonicalLoop(OMPCanonicalLoop
*L
) {
9265 // OMPCanonicalLoops are eliminated during transformation, since they will be
9266 // recomputed by semantic analysis of the associated OMPLoopBasedDirective
9267 // after transformation.
9268 return getDerived().TransformStmt(L
->getLoopStmt());
9271 template <typename Derived
>
9272 StmtResult TreeTransform
<Derived
>::TransformOMPExecutableDirective(
9273 OMPExecutableDirective
*D
) {
9275 // Transform the clauses
9276 llvm::SmallVector
<OMPClause
*, 16> TClauses
;
9277 ArrayRef
<OMPClause
*> Clauses
= D
->clauses();
9278 TClauses
.reserve(Clauses
.size());
9279 for (ArrayRef
<OMPClause
*>::iterator I
= Clauses
.begin(), E
= Clauses
.end();
9282 getDerived().getSema().OpenMP().StartOpenMPClause((*I
)->getClauseKind());
9283 OMPClause
*Clause
= getDerived().TransformOMPClause(*I
);
9284 getDerived().getSema().OpenMP().EndOpenMPClause();
9286 TClauses
.push_back(Clause
);
9288 TClauses
.push_back(nullptr);
9291 StmtResult AssociatedStmt
;
9292 if (D
->hasAssociatedStmt() && D
->getAssociatedStmt()) {
9293 getDerived().getSema().OpenMP().ActOnOpenMPRegionStart(
9294 D
->getDirectiveKind(),
9295 /*CurScope=*/nullptr);
9298 Sema::CompoundScopeRAII
CompoundScope(getSema());
9300 if (D
->getDirectiveKind() == OMPD_atomic
||
9301 D
->getDirectiveKind() == OMPD_critical
||
9302 D
->getDirectiveKind() == OMPD_section
||
9303 D
->getDirectiveKind() == OMPD_master
)
9304 CS
= D
->getAssociatedStmt();
9306 CS
= D
->getRawStmt();
9307 Body
= getDerived().TransformStmt(CS
);
9308 if (Body
.isUsable() && isOpenMPLoopDirective(D
->getDirectiveKind()) &&
9309 getSema().getLangOpts().OpenMPIRBuilder
)
9310 Body
= getDerived().RebuildOMPCanonicalLoop(Body
.get());
9313 getDerived().getSema().OpenMP().ActOnOpenMPRegionEnd(Body
, TClauses
);
9314 if (AssociatedStmt
.isInvalid()) {
9318 if (TClauses
.size() != Clauses
.size()) {
9322 // Transform directive name for 'omp critical' directive.
9323 DeclarationNameInfo DirName
;
9324 if (D
->getDirectiveKind() == OMPD_critical
) {
9325 DirName
= cast
<OMPCriticalDirective
>(D
)->getDirectiveName();
9326 DirName
= getDerived().TransformDeclarationNameInfo(DirName
);
9328 OpenMPDirectiveKind CancelRegion
= OMPD_unknown
;
9329 if (D
->getDirectiveKind() == OMPD_cancellation_point
) {
9330 CancelRegion
= cast
<OMPCancellationPointDirective
>(D
)->getCancelRegion();
9331 } else if (D
->getDirectiveKind() == OMPD_cancel
) {
9332 CancelRegion
= cast
<OMPCancelDirective
>(D
)->getCancelRegion();
9335 return getDerived().RebuildOMPExecutableDirective(
9336 D
->getDirectiveKind(), DirName
, CancelRegion
, TClauses
,
9337 AssociatedStmt
.get(), D
->getBeginLoc(), D
->getEndLoc());
9340 /// This is mostly the same as above, but allows 'informational' class
9341 /// directives when rebuilding the stmt. It still takes an
9342 /// OMPExecutableDirective-type argument because we're reusing that as the
9343 /// superclass for the 'assume' directive at present, instead of defining a
9344 /// mostly-identical OMPInformationalDirective parent class.
9345 template <typename Derived
>
9346 StmtResult TreeTransform
<Derived
>::TransformOMPInformationalDirective(
9347 OMPExecutableDirective
*D
) {
9349 // Transform the clauses
9350 llvm::SmallVector
<OMPClause
*, 16> TClauses
;
9351 ArrayRef
<OMPClause
*> Clauses
= D
->clauses();
9352 TClauses
.reserve(Clauses
.size());
9353 for (OMPClause
*C
: Clauses
) {
9355 getDerived().getSema().OpenMP().StartOpenMPClause(C
->getClauseKind());
9356 OMPClause
*Clause
= getDerived().TransformOMPClause(C
);
9357 getDerived().getSema().OpenMP().EndOpenMPClause();
9359 TClauses
.push_back(Clause
);
9361 TClauses
.push_back(nullptr);
9364 StmtResult AssociatedStmt
;
9365 if (D
->hasAssociatedStmt() && D
->getAssociatedStmt()) {
9366 getDerived().getSema().OpenMP().ActOnOpenMPRegionStart(
9367 D
->getDirectiveKind(),
9368 /*CurScope=*/nullptr);
9371 Sema::CompoundScopeRAII
CompoundScope(getSema());
9372 assert(D
->getDirectiveKind() == OMPD_assume
&&
9373 "Unexpected informational directive");
9374 Stmt
*CS
= D
->getAssociatedStmt();
9375 Body
= getDerived().TransformStmt(CS
);
9378 getDerived().getSema().OpenMP().ActOnOpenMPRegionEnd(Body
, TClauses
);
9379 if (AssociatedStmt
.isInvalid())
9382 if (TClauses
.size() != Clauses
.size())
9385 DeclarationNameInfo DirName
;
9387 return getDerived().RebuildOMPInformationalDirective(
9388 D
->getDirectiveKind(), DirName
, TClauses
, AssociatedStmt
.get(),
9389 D
->getBeginLoc(), D
->getEndLoc());
9392 template <typename Derived
>
9394 TreeTransform
<Derived
>::TransformOMPMetaDirective(OMPMetaDirective
*D
) {
9396 SemaRef
.Diag(D
->getBeginLoc(), diag::err_omp_instantiation_not_supported
)
9397 << getOpenMPDirectiveName(D
->getDirectiveKind());
9401 template <typename Derived
>
9403 TreeTransform
<Derived
>::TransformOMPParallelDirective(OMPParallelDirective
*D
) {
9404 DeclarationNameInfo DirName
;
9405 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9406 OMPD_parallel
, DirName
, nullptr, D
->getBeginLoc());
9407 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9408 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9412 template <typename Derived
>
9414 TreeTransform
<Derived
>::TransformOMPSimdDirective(OMPSimdDirective
*D
) {
9415 DeclarationNameInfo DirName
;
9416 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9417 OMPD_simd
, DirName
, nullptr, D
->getBeginLoc());
9418 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9419 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9423 template <typename Derived
>
9425 TreeTransform
<Derived
>::TransformOMPTileDirective(OMPTileDirective
*D
) {
9426 DeclarationNameInfo DirName
;
9427 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9428 D
->getDirectiveKind(), DirName
, nullptr, D
->getBeginLoc());
9429 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9430 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9434 template <typename Derived
>
9436 TreeTransform
<Derived
>::TransformOMPUnrollDirective(OMPUnrollDirective
*D
) {
9437 DeclarationNameInfo DirName
;
9438 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9439 D
->getDirectiveKind(), DirName
, nullptr, D
->getBeginLoc());
9440 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9441 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9445 template <typename Derived
>
9447 TreeTransform
<Derived
>::TransformOMPReverseDirective(OMPReverseDirective
*D
) {
9448 DeclarationNameInfo DirName
;
9449 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9450 D
->getDirectiveKind(), DirName
, nullptr, D
->getBeginLoc());
9451 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9452 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9456 template <typename Derived
>
9457 StmtResult TreeTransform
<Derived
>::TransformOMPInterchangeDirective(
9458 OMPInterchangeDirective
*D
) {
9459 DeclarationNameInfo DirName
;
9460 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9461 D
->getDirectiveKind(), DirName
, nullptr, D
->getBeginLoc());
9462 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9463 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9467 template <typename Derived
>
9469 TreeTransform
<Derived
>::TransformOMPForDirective(OMPForDirective
*D
) {
9470 DeclarationNameInfo DirName
;
9471 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9472 OMPD_for
, DirName
, nullptr, D
->getBeginLoc());
9473 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9474 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9478 template <typename Derived
>
9480 TreeTransform
<Derived
>::TransformOMPForSimdDirective(OMPForSimdDirective
*D
) {
9481 DeclarationNameInfo DirName
;
9482 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9483 OMPD_for_simd
, DirName
, nullptr, D
->getBeginLoc());
9484 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9485 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9489 template <typename Derived
>
9491 TreeTransform
<Derived
>::TransformOMPSectionsDirective(OMPSectionsDirective
*D
) {
9492 DeclarationNameInfo DirName
;
9493 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9494 OMPD_sections
, DirName
, nullptr, D
->getBeginLoc());
9495 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9496 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9500 template <typename Derived
>
9502 TreeTransform
<Derived
>::TransformOMPSectionDirective(OMPSectionDirective
*D
) {
9503 DeclarationNameInfo DirName
;
9504 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9505 OMPD_section
, DirName
, nullptr, D
->getBeginLoc());
9506 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9507 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9511 template <typename Derived
>
9513 TreeTransform
<Derived
>::TransformOMPScopeDirective(OMPScopeDirective
*D
) {
9514 DeclarationNameInfo DirName
;
9515 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9516 OMPD_scope
, DirName
, nullptr, D
->getBeginLoc());
9517 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9518 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9522 template <typename Derived
>
9524 TreeTransform
<Derived
>::TransformOMPSingleDirective(OMPSingleDirective
*D
) {
9525 DeclarationNameInfo DirName
;
9526 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9527 OMPD_single
, DirName
, nullptr, D
->getBeginLoc());
9528 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9529 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9533 template <typename Derived
>
9535 TreeTransform
<Derived
>::TransformOMPMasterDirective(OMPMasterDirective
*D
) {
9536 DeclarationNameInfo DirName
;
9537 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9538 OMPD_master
, DirName
, nullptr, D
->getBeginLoc());
9539 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9540 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9544 template <typename Derived
>
9546 TreeTransform
<Derived
>::TransformOMPCriticalDirective(OMPCriticalDirective
*D
) {
9547 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9548 OMPD_critical
, D
->getDirectiveName(), nullptr, D
->getBeginLoc());
9549 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9550 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9554 template <typename Derived
>
9555 StmtResult TreeTransform
<Derived
>::TransformOMPParallelForDirective(
9556 OMPParallelForDirective
*D
) {
9557 DeclarationNameInfo DirName
;
9558 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9559 OMPD_parallel_for
, DirName
, nullptr, D
->getBeginLoc());
9560 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9561 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9565 template <typename Derived
>
9566 StmtResult TreeTransform
<Derived
>::TransformOMPParallelForSimdDirective(
9567 OMPParallelForSimdDirective
*D
) {
9568 DeclarationNameInfo DirName
;
9569 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9570 OMPD_parallel_for_simd
, DirName
, nullptr, D
->getBeginLoc());
9571 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9572 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9576 template <typename Derived
>
9577 StmtResult TreeTransform
<Derived
>::TransformOMPParallelMasterDirective(
9578 OMPParallelMasterDirective
*D
) {
9579 DeclarationNameInfo DirName
;
9580 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9581 OMPD_parallel_master
, DirName
, nullptr, D
->getBeginLoc());
9582 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9583 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9587 template <typename Derived
>
9588 StmtResult TreeTransform
<Derived
>::TransformOMPParallelMaskedDirective(
9589 OMPParallelMaskedDirective
*D
) {
9590 DeclarationNameInfo DirName
;
9591 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9592 OMPD_parallel_masked
, DirName
, nullptr, D
->getBeginLoc());
9593 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9594 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9598 template <typename Derived
>
9599 StmtResult TreeTransform
<Derived
>::TransformOMPParallelSectionsDirective(
9600 OMPParallelSectionsDirective
*D
) {
9601 DeclarationNameInfo DirName
;
9602 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9603 OMPD_parallel_sections
, DirName
, nullptr, D
->getBeginLoc());
9604 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9605 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9609 template <typename Derived
>
9611 TreeTransform
<Derived
>::TransformOMPTaskDirective(OMPTaskDirective
*D
) {
9612 DeclarationNameInfo DirName
;
9613 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9614 OMPD_task
, DirName
, nullptr, D
->getBeginLoc());
9615 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9616 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9620 template <typename Derived
>
9621 StmtResult TreeTransform
<Derived
>::TransformOMPTaskyieldDirective(
9622 OMPTaskyieldDirective
*D
) {
9623 DeclarationNameInfo DirName
;
9624 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9625 OMPD_taskyield
, DirName
, nullptr, D
->getBeginLoc());
9626 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9627 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9631 template <typename Derived
>
9633 TreeTransform
<Derived
>::TransformOMPBarrierDirective(OMPBarrierDirective
*D
) {
9634 DeclarationNameInfo DirName
;
9635 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9636 OMPD_barrier
, DirName
, nullptr, D
->getBeginLoc());
9637 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9638 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9642 template <typename Derived
>
9644 TreeTransform
<Derived
>::TransformOMPTaskwaitDirective(OMPTaskwaitDirective
*D
) {
9645 DeclarationNameInfo DirName
;
9646 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9647 OMPD_taskwait
, DirName
, nullptr, D
->getBeginLoc());
9648 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9649 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9653 template <typename Derived
>
9655 TreeTransform
<Derived
>::TransformOMPAssumeDirective(OMPAssumeDirective
*D
) {
9656 DeclarationNameInfo DirName
;
9657 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9658 OMPD_assume
, DirName
, nullptr, D
->getBeginLoc());
9659 StmtResult Res
= getDerived().TransformOMPInformationalDirective(D
);
9660 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9664 template <typename Derived
>
9666 TreeTransform
<Derived
>::TransformOMPErrorDirective(OMPErrorDirective
*D
) {
9667 DeclarationNameInfo DirName
;
9668 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9669 OMPD_error
, DirName
, nullptr, D
->getBeginLoc());
9670 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9671 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9675 template <typename Derived
>
9676 StmtResult TreeTransform
<Derived
>::TransformOMPTaskgroupDirective(
9677 OMPTaskgroupDirective
*D
) {
9678 DeclarationNameInfo DirName
;
9679 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9680 OMPD_taskgroup
, DirName
, nullptr, D
->getBeginLoc());
9681 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9682 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9686 template <typename Derived
>
9688 TreeTransform
<Derived
>::TransformOMPFlushDirective(OMPFlushDirective
*D
) {
9689 DeclarationNameInfo DirName
;
9690 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9691 OMPD_flush
, DirName
, nullptr, D
->getBeginLoc());
9692 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9693 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9697 template <typename Derived
>
9699 TreeTransform
<Derived
>::TransformOMPDepobjDirective(OMPDepobjDirective
*D
) {
9700 DeclarationNameInfo DirName
;
9701 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9702 OMPD_depobj
, DirName
, nullptr, D
->getBeginLoc());
9703 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9704 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9708 template <typename Derived
>
9710 TreeTransform
<Derived
>::TransformOMPScanDirective(OMPScanDirective
*D
) {
9711 DeclarationNameInfo DirName
;
9712 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9713 OMPD_scan
, DirName
, nullptr, D
->getBeginLoc());
9714 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9715 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9719 template <typename Derived
>
9721 TreeTransform
<Derived
>::TransformOMPOrderedDirective(OMPOrderedDirective
*D
) {
9722 DeclarationNameInfo DirName
;
9723 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9724 OMPD_ordered
, DirName
, nullptr, D
->getBeginLoc());
9725 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9726 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9730 template <typename Derived
>
9732 TreeTransform
<Derived
>::TransformOMPAtomicDirective(OMPAtomicDirective
*D
) {
9733 DeclarationNameInfo DirName
;
9734 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9735 OMPD_atomic
, DirName
, nullptr, D
->getBeginLoc());
9736 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9737 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9741 template <typename Derived
>
9743 TreeTransform
<Derived
>::TransformOMPTargetDirective(OMPTargetDirective
*D
) {
9744 DeclarationNameInfo DirName
;
9745 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9746 OMPD_target
, DirName
, nullptr, D
->getBeginLoc());
9747 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9748 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9752 template <typename Derived
>
9753 StmtResult TreeTransform
<Derived
>::TransformOMPTargetDataDirective(
9754 OMPTargetDataDirective
*D
) {
9755 DeclarationNameInfo DirName
;
9756 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9757 OMPD_target_data
, DirName
, nullptr, D
->getBeginLoc());
9758 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9759 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9763 template <typename Derived
>
9764 StmtResult TreeTransform
<Derived
>::TransformOMPTargetEnterDataDirective(
9765 OMPTargetEnterDataDirective
*D
) {
9766 DeclarationNameInfo DirName
;
9767 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9768 OMPD_target_enter_data
, DirName
, nullptr, D
->getBeginLoc());
9769 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9770 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9774 template <typename Derived
>
9775 StmtResult TreeTransform
<Derived
>::TransformOMPTargetExitDataDirective(
9776 OMPTargetExitDataDirective
*D
) {
9777 DeclarationNameInfo DirName
;
9778 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9779 OMPD_target_exit_data
, DirName
, nullptr, D
->getBeginLoc());
9780 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9781 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9785 template <typename Derived
>
9786 StmtResult TreeTransform
<Derived
>::TransformOMPTargetParallelDirective(
9787 OMPTargetParallelDirective
*D
) {
9788 DeclarationNameInfo DirName
;
9789 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9790 OMPD_target_parallel
, DirName
, nullptr, D
->getBeginLoc());
9791 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9792 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9796 template <typename Derived
>
9797 StmtResult TreeTransform
<Derived
>::TransformOMPTargetParallelForDirective(
9798 OMPTargetParallelForDirective
*D
) {
9799 DeclarationNameInfo DirName
;
9800 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9801 OMPD_target_parallel_for
, DirName
, nullptr, D
->getBeginLoc());
9802 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9803 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9807 template <typename Derived
>
9808 StmtResult TreeTransform
<Derived
>::TransformOMPTargetUpdateDirective(
9809 OMPTargetUpdateDirective
*D
) {
9810 DeclarationNameInfo DirName
;
9811 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9812 OMPD_target_update
, DirName
, nullptr, D
->getBeginLoc());
9813 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9814 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9818 template <typename Derived
>
9820 TreeTransform
<Derived
>::TransformOMPTeamsDirective(OMPTeamsDirective
*D
) {
9821 DeclarationNameInfo DirName
;
9822 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9823 OMPD_teams
, DirName
, nullptr, D
->getBeginLoc());
9824 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9825 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9829 template <typename Derived
>
9830 StmtResult TreeTransform
<Derived
>::TransformOMPCancellationPointDirective(
9831 OMPCancellationPointDirective
*D
) {
9832 DeclarationNameInfo DirName
;
9833 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9834 OMPD_cancellation_point
, DirName
, nullptr, D
->getBeginLoc());
9835 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9836 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9840 template <typename Derived
>
9842 TreeTransform
<Derived
>::TransformOMPCancelDirective(OMPCancelDirective
*D
) {
9843 DeclarationNameInfo DirName
;
9844 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9845 OMPD_cancel
, DirName
, nullptr, D
->getBeginLoc());
9846 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9847 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9851 template <typename Derived
>
9853 TreeTransform
<Derived
>::TransformOMPTaskLoopDirective(OMPTaskLoopDirective
*D
) {
9854 DeclarationNameInfo DirName
;
9855 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9856 OMPD_taskloop
, DirName
, nullptr, D
->getBeginLoc());
9857 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9858 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9862 template <typename Derived
>
9863 StmtResult TreeTransform
<Derived
>::TransformOMPTaskLoopSimdDirective(
9864 OMPTaskLoopSimdDirective
*D
) {
9865 DeclarationNameInfo DirName
;
9866 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9867 OMPD_taskloop_simd
, DirName
, nullptr, D
->getBeginLoc());
9868 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9869 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9873 template <typename Derived
>
9874 StmtResult TreeTransform
<Derived
>::TransformOMPMasterTaskLoopDirective(
9875 OMPMasterTaskLoopDirective
*D
) {
9876 DeclarationNameInfo DirName
;
9877 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9878 OMPD_master_taskloop
, DirName
, nullptr, D
->getBeginLoc());
9879 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9880 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9884 template <typename Derived
>
9885 StmtResult TreeTransform
<Derived
>::TransformOMPMaskedTaskLoopDirective(
9886 OMPMaskedTaskLoopDirective
*D
) {
9887 DeclarationNameInfo DirName
;
9888 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9889 OMPD_masked_taskloop
, DirName
, nullptr, D
->getBeginLoc());
9890 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9891 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9895 template <typename Derived
>
9896 StmtResult TreeTransform
<Derived
>::TransformOMPMasterTaskLoopSimdDirective(
9897 OMPMasterTaskLoopSimdDirective
*D
) {
9898 DeclarationNameInfo DirName
;
9899 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9900 OMPD_master_taskloop_simd
, DirName
, nullptr, D
->getBeginLoc());
9901 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9902 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9906 template <typename Derived
>
9907 StmtResult TreeTransform
<Derived
>::TransformOMPMaskedTaskLoopSimdDirective(
9908 OMPMaskedTaskLoopSimdDirective
*D
) {
9909 DeclarationNameInfo DirName
;
9910 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9911 OMPD_masked_taskloop_simd
, DirName
, nullptr, D
->getBeginLoc());
9912 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9913 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9917 template <typename Derived
>
9918 StmtResult TreeTransform
<Derived
>::TransformOMPParallelMasterTaskLoopDirective(
9919 OMPParallelMasterTaskLoopDirective
*D
) {
9920 DeclarationNameInfo DirName
;
9921 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9922 OMPD_parallel_master_taskloop
, DirName
, nullptr, D
->getBeginLoc());
9923 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9924 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9928 template <typename Derived
>
9929 StmtResult TreeTransform
<Derived
>::TransformOMPParallelMaskedTaskLoopDirective(
9930 OMPParallelMaskedTaskLoopDirective
*D
) {
9931 DeclarationNameInfo DirName
;
9932 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9933 OMPD_parallel_masked_taskloop
, DirName
, nullptr, D
->getBeginLoc());
9934 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9935 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9939 template <typename Derived
>
9941 TreeTransform
<Derived
>::TransformOMPParallelMasterTaskLoopSimdDirective(
9942 OMPParallelMasterTaskLoopSimdDirective
*D
) {
9943 DeclarationNameInfo DirName
;
9944 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9945 OMPD_parallel_master_taskloop_simd
, DirName
, nullptr, D
->getBeginLoc());
9946 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9947 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9951 template <typename Derived
>
9953 TreeTransform
<Derived
>::TransformOMPParallelMaskedTaskLoopSimdDirective(
9954 OMPParallelMaskedTaskLoopSimdDirective
*D
) {
9955 DeclarationNameInfo DirName
;
9956 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9957 OMPD_parallel_masked_taskloop_simd
, DirName
, nullptr, D
->getBeginLoc());
9958 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9959 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9963 template <typename Derived
>
9964 StmtResult TreeTransform
<Derived
>::TransformOMPDistributeDirective(
9965 OMPDistributeDirective
*D
) {
9966 DeclarationNameInfo DirName
;
9967 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9968 OMPD_distribute
, DirName
, nullptr, D
->getBeginLoc());
9969 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9970 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9974 template <typename Derived
>
9975 StmtResult TreeTransform
<Derived
>::TransformOMPDistributeParallelForDirective(
9976 OMPDistributeParallelForDirective
*D
) {
9977 DeclarationNameInfo DirName
;
9978 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9979 OMPD_distribute_parallel_for
, DirName
, nullptr, D
->getBeginLoc());
9980 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9981 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9985 template <typename Derived
>
9987 TreeTransform
<Derived
>::TransformOMPDistributeParallelForSimdDirective(
9988 OMPDistributeParallelForSimdDirective
*D
) {
9989 DeclarationNameInfo DirName
;
9990 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
9991 OMPD_distribute_parallel_for_simd
, DirName
, nullptr, D
->getBeginLoc());
9992 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
9993 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
9997 template <typename Derived
>
9998 StmtResult TreeTransform
<Derived
>::TransformOMPDistributeSimdDirective(
9999 OMPDistributeSimdDirective
*D
) {
10000 DeclarationNameInfo DirName
;
10001 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10002 OMPD_distribute_simd
, DirName
, nullptr, D
->getBeginLoc());
10003 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10004 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10008 template <typename Derived
>
10009 StmtResult TreeTransform
<Derived
>::TransformOMPTargetParallelForSimdDirective(
10010 OMPTargetParallelForSimdDirective
*D
) {
10011 DeclarationNameInfo DirName
;
10012 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10013 OMPD_target_parallel_for_simd
, DirName
, nullptr, D
->getBeginLoc());
10014 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10015 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10019 template <typename Derived
>
10020 StmtResult TreeTransform
<Derived
>::TransformOMPTargetSimdDirective(
10021 OMPTargetSimdDirective
*D
) {
10022 DeclarationNameInfo DirName
;
10023 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10024 OMPD_target_simd
, DirName
, nullptr, D
->getBeginLoc());
10025 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10026 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10030 template <typename Derived
>
10031 StmtResult TreeTransform
<Derived
>::TransformOMPTeamsDistributeDirective(
10032 OMPTeamsDistributeDirective
*D
) {
10033 DeclarationNameInfo DirName
;
10034 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10035 OMPD_teams_distribute
, DirName
, nullptr, D
->getBeginLoc());
10036 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10037 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10041 template <typename Derived
>
10042 StmtResult TreeTransform
<Derived
>::TransformOMPTeamsDistributeSimdDirective(
10043 OMPTeamsDistributeSimdDirective
*D
) {
10044 DeclarationNameInfo DirName
;
10045 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10046 OMPD_teams_distribute_simd
, DirName
, nullptr, D
->getBeginLoc());
10047 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10048 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10052 template <typename Derived
>
10053 StmtResult TreeTransform
<Derived
>::TransformOMPTeamsDistributeParallelForSimdDirective(
10054 OMPTeamsDistributeParallelForSimdDirective
*D
) {
10055 DeclarationNameInfo DirName
;
10056 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10057 OMPD_teams_distribute_parallel_for_simd
, DirName
, nullptr,
10059 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10060 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10064 template <typename Derived
>
10065 StmtResult TreeTransform
<Derived
>::TransformOMPTeamsDistributeParallelForDirective(
10066 OMPTeamsDistributeParallelForDirective
*D
) {
10067 DeclarationNameInfo DirName
;
10068 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10069 OMPD_teams_distribute_parallel_for
, DirName
, nullptr, D
->getBeginLoc());
10070 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10071 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10075 template <typename Derived
>
10076 StmtResult TreeTransform
<Derived
>::TransformOMPTargetTeamsDirective(
10077 OMPTargetTeamsDirective
*D
) {
10078 DeclarationNameInfo DirName
;
10079 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10080 OMPD_target_teams
, DirName
, nullptr, D
->getBeginLoc());
10081 auto Res
= getDerived().TransformOMPExecutableDirective(D
);
10082 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10086 template <typename Derived
>
10087 StmtResult TreeTransform
<Derived
>::TransformOMPTargetTeamsDistributeDirective(
10088 OMPTargetTeamsDistributeDirective
*D
) {
10089 DeclarationNameInfo DirName
;
10090 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10091 OMPD_target_teams_distribute
, DirName
, nullptr, D
->getBeginLoc());
10092 auto Res
= getDerived().TransformOMPExecutableDirective(D
);
10093 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10097 template <typename Derived
>
10099 TreeTransform
<Derived
>::TransformOMPTargetTeamsDistributeParallelForDirective(
10100 OMPTargetTeamsDistributeParallelForDirective
*D
) {
10101 DeclarationNameInfo DirName
;
10102 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10103 OMPD_target_teams_distribute_parallel_for
, DirName
, nullptr,
10105 auto Res
= getDerived().TransformOMPExecutableDirective(D
);
10106 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10110 template <typename Derived
>
10111 StmtResult TreeTransform
<Derived
>::
10112 TransformOMPTargetTeamsDistributeParallelForSimdDirective(
10113 OMPTargetTeamsDistributeParallelForSimdDirective
*D
) {
10114 DeclarationNameInfo DirName
;
10115 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10116 OMPD_target_teams_distribute_parallel_for_simd
, DirName
, nullptr,
10118 auto Res
= getDerived().TransformOMPExecutableDirective(D
);
10119 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10123 template <typename Derived
>
10125 TreeTransform
<Derived
>::TransformOMPTargetTeamsDistributeSimdDirective(
10126 OMPTargetTeamsDistributeSimdDirective
*D
) {
10127 DeclarationNameInfo DirName
;
10128 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10129 OMPD_target_teams_distribute_simd
, DirName
, nullptr, D
->getBeginLoc());
10130 auto Res
= getDerived().TransformOMPExecutableDirective(D
);
10131 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10135 template <typename Derived
>
10137 TreeTransform
<Derived
>::TransformOMPInteropDirective(OMPInteropDirective
*D
) {
10138 DeclarationNameInfo DirName
;
10139 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10140 OMPD_interop
, DirName
, nullptr, D
->getBeginLoc());
10141 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10142 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10146 template <typename Derived
>
10148 TreeTransform
<Derived
>::TransformOMPDispatchDirective(OMPDispatchDirective
*D
) {
10149 DeclarationNameInfo DirName
;
10150 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10151 OMPD_dispatch
, DirName
, nullptr, D
->getBeginLoc());
10152 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10153 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10157 template <typename Derived
>
10159 TreeTransform
<Derived
>::TransformOMPMaskedDirective(OMPMaskedDirective
*D
) {
10160 DeclarationNameInfo DirName
;
10161 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10162 OMPD_masked
, DirName
, nullptr, D
->getBeginLoc());
10163 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10164 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10168 template <typename Derived
>
10169 StmtResult TreeTransform
<Derived
>::TransformOMPGenericLoopDirective(
10170 OMPGenericLoopDirective
*D
) {
10171 DeclarationNameInfo DirName
;
10172 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10173 OMPD_loop
, DirName
, nullptr, D
->getBeginLoc());
10174 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10175 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10179 template <typename Derived
>
10180 StmtResult TreeTransform
<Derived
>::TransformOMPTeamsGenericLoopDirective(
10181 OMPTeamsGenericLoopDirective
*D
) {
10182 DeclarationNameInfo DirName
;
10183 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10184 OMPD_teams_loop
, DirName
, nullptr, D
->getBeginLoc());
10185 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10186 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10190 template <typename Derived
>
10191 StmtResult TreeTransform
<Derived
>::TransformOMPTargetTeamsGenericLoopDirective(
10192 OMPTargetTeamsGenericLoopDirective
*D
) {
10193 DeclarationNameInfo DirName
;
10194 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10195 OMPD_target_teams_loop
, DirName
, nullptr, D
->getBeginLoc());
10196 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10197 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10201 template <typename Derived
>
10202 StmtResult TreeTransform
<Derived
>::TransformOMPParallelGenericLoopDirective(
10203 OMPParallelGenericLoopDirective
*D
) {
10204 DeclarationNameInfo DirName
;
10205 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10206 OMPD_parallel_loop
, DirName
, nullptr, D
->getBeginLoc());
10207 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10208 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10212 template <typename Derived
>
10214 TreeTransform
<Derived
>::TransformOMPTargetParallelGenericLoopDirective(
10215 OMPTargetParallelGenericLoopDirective
*D
) {
10216 DeclarationNameInfo DirName
;
10217 getDerived().getSema().OpenMP().StartOpenMPDSABlock(
10218 OMPD_target_parallel_loop
, DirName
, nullptr, D
->getBeginLoc());
10219 StmtResult Res
= getDerived().TransformOMPExecutableDirective(D
);
10220 getDerived().getSema().OpenMP().EndOpenMPDSABlock(Res
.get());
10224 //===----------------------------------------------------------------------===//
10225 // OpenMP clause transformation
10226 //===----------------------------------------------------------------------===//
10227 template <typename Derived
>
10228 OMPClause
*TreeTransform
<Derived
>::TransformOMPIfClause(OMPIfClause
*C
) {
10229 ExprResult Cond
= getDerived().TransformExpr(C
->getCondition());
10230 if (Cond
.isInvalid())
10232 return getDerived().RebuildOMPIfClause(
10233 C
->getNameModifier(), Cond
.get(), C
->getBeginLoc(), C
->getLParenLoc(),
10234 C
->getNameModifierLoc(), C
->getColonLoc(), C
->getEndLoc());
10237 template <typename Derived
>
10238 OMPClause
*TreeTransform
<Derived
>::TransformOMPFinalClause(OMPFinalClause
*C
) {
10239 ExprResult Cond
= getDerived().TransformExpr(C
->getCondition());
10240 if (Cond
.isInvalid())
10242 return getDerived().RebuildOMPFinalClause(Cond
.get(), C
->getBeginLoc(),
10243 C
->getLParenLoc(), C
->getEndLoc());
10246 template <typename Derived
>
10248 TreeTransform
<Derived
>::TransformOMPNumThreadsClause(OMPNumThreadsClause
*C
) {
10249 ExprResult NumThreads
= getDerived().TransformExpr(C
->getNumThreads());
10250 if (NumThreads
.isInvalid())
10252 return getDerived().RebuildOMPNumThreadsClause(
10253 NumThreads
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10256 template <typename Derived
>
10258 TreeTransform
<Derived
>::TransformOMPSafelenClause(OMPSafelenClause
*C
) {
10259 ExprResult E
= getDerived().TransformExpr(C
->getSafelen());
10262 return getDerived().RebuildOMPSafelenClause(
10263 E
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10266 template <typename Derived
>
10268 TreeTransform
<Derived
>::TransformOMPAllocatorClause(OMPAllocatorClause
*C
) {
10269 ExprResult E
= getDerived().TransformExpr(C
->getAllocator());
10272 return getDerived().RebuildOMPAllocatorClause(
10273 E
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10276 template <typename Derived
>
10278 TreeTransform
<Derived
>::TransformOMPSimdlenClause(OMPSimdlenClause
*C
) {
10279 ExprResult E
= getDerived().TransformExpr(C
->getSimdlen());
10282 return getDerived().RebuildOMPSimdlenClause(
10283 E
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10286 template <typename Derived
>
10287 OMPClause
*TreeTransform
<Derived
>::TransformOMPSizesClause(OMPSizesClause
*C
) {
10288 SmallVector
<Expr
*, 4> TransformedSizes
;
10289 TransformedSizes
.reserve(C
->getNumSizes());
10290 bool Changed
= false;
10291 for (Expr
*E
: C
->getSizesRefs()) {
10293 TransformedSizes
.push_back(nullptr);
10297 ExprResult T
= getDerived().TransformExpr(E
);
10302 TransformedSizes
.push_back(T
.get());
10305 if (!Changed
&& !getDerived().AlwaysRebuild())
10307 return RebuildOMPSizesClause(TransformedSizes
, C
->getBeginLoc(),
10308 C
->getLParenLoc(), C
->getEndLoc());
10311 template <typename Derived
>
10313 TreeTransform
<Derived
>::TransformOMPPermutationClause(OMPPermutationClause
*C
) {
10314 SmallVector
<Expr
*> TransformedArgs
;
10315 TransformedArgs
.reserve(C
->getNumLoops());
10316 bool Changed
= false;
10317 for (Expr
*E
: C
->getArgsRefs()) {
10319 TransformedArgs
.push_back(nullptr);
10323 ExprResult T
= getDerived().TransformExpr(E
);
10328 TransformedArgs
.push_back(T
.get());
10331 if (!Changed
&& !getDerived().AlwaysRebuild())
10333 return RebuildOMPPermutationClause(TransformedArgs
, C
->getBeginLoc(),
10334 C
->getLParenLoc(), C
->getEndLoc());
10337 template <typename Derived
>
10338 OMPClause
*TreeTransform
<Derived
>::TransformOMPFullClause(OMPFullClause
*C
) {
10339 if (!getDerived().AlwaysRebuild())
10341 return RebuildOMPFullClause(C
->getBeginLoc(), C
->getEndLoc());
10344 template <typename Derived
>
10346 TreeTransform
<Derived
>::TransformOMPPartialClause(OMPPartialClause
*C
) {
10347 ExprResult T
= getDerived().TransformExpr(C
->getFactor());
10350 Expr
*Factor
= T
.get();
10351 bool Changed
= Factor
!= C
->getFactor();
10353 if (!Changed
&& !getDerived().AlwaysRebuild())
10355 return RebuildOMPPartialClause(Factor
, C
->getBeginLoc(), C
->getLParenLoc(),
10359 template <typename Derived
>
10361 TreeTransform
<Derived
>::TransformOMPCollapseClause(OMPCollapseClause
*C
) {
10362 ExprResult E
= getDerived().TransformExpr(C
->getNumForLoops());
10365 return getDerived().RebuildOMPCollapseClause(
10366 E
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10369 template <typename Derived
>
10371 TreeTransform
<Derived
>::TransformOMPDefaultClause(OMPDefaultClause
*C
) {
10372 return getDerived().RebuildOMPDefaultClause(
10373 C
->getDefaultKind(), C
->getDefaultKindKwLoc(), C
->getBeginLoc(),
10374 C
->getLParenLoc(), C
->getEndLoc());
10377 template <typename Derived
>
10379 TreeTransform
<Derived
>::TransformOMPProcBindClause(OMPProcBindClause
*C
) {
10380 return getDerived().RebuildOMPProcBindClause(
10381 C
->getProcBindKind(), C
->getProcBindKindKwLoc(), C
->getBeginLoc(),
10382 C
->getLParenLoc(), C
->getEndLoc());
10385 template <typename Derived
>
10387 TreeTransform
<Derived
>::TransformOMPScheduleClause(OMPScheduleClause
*C
) {
10388 ExprResult E
= getDerived().TransformExpr(C
->getChunkSize());
10391 return getDerived().RebuildOMPScheduleClause(
10392 C
->getFirstScheduleModifier(), C
->getSecondScheduleModifier(),
10393 C
->getScheduleKind(), E
.get(), C
->getBeginLoc(), C
->getLParenLoc(),
10394 C
->getFirstScheduleModifierLoc(), C
->getSecondScheduleModifierLoc(),
10395 C
->getScheduleKindLoc(), C
->getCommaLoc(), C
->getEndLoc());
10398 template <typename Derived
>
10400 TreeTransform
<Derived
>::TransformOMPOrderedClause(OMPOrderedClause
*C
) {
10402 if (auto *Num
= C
->getNumForLoops()) {
10403 E
= getDerived().TransformExpr(Num
);
10407 return getDerived().RebuildOMPOrderedClause(C
->getBeginLoc(), C
->getEndLoc(),
10408 C
->getLParenLoc(), E
.get());
10411 template <typename Derived
>
10413 TreeTransform
<Derived
>::TransformOMPDetachClause(OMPDetachClause
*C
) {
10415 if (Expr
*Evt
= C
->getEventHandler()) {
10416 E
= getDerived().TransformExpr(Evt
);
10420 return getDerived().RebuildOMPDetachClause(E
.get(), C
->getBeginLoc(),
10421 C
->getLParenLoc(), C
->getEndLoc());
10424 template <typename Derived
>
10426 TreeTransform
<Derived
>::TransformOMPNowaitClause(OMPNowaitClause
*C
) {
10427 // No need to rebuild this clause, no template-dependent parameters.
10431 template <typename Derived
>
10433 TreeTransform
<Derived
>::TransformOMPUntiedClause(OMPUntiedClause
*C
) {
10434 // No need to rebuild this clause, no template-dependent parameters.
10438 template <typename Derived
>
10440 TreeTransform
<Derived
>::TransformOMPMergeableClause(OMPMergeableClause
*C
) {
10441 // No need to rebuild this clause, no template-dependent parameters.
10445 template <typename Derived
>
10446 OMPClause
*TreeTransform
<Derived
>::TransformOMPReadClause(OMPReadClause
*C
) {
10447 // No need to rebuild this clause, no template-dependent parameters.
10451 template <typename Derived
>
10452 OMPClause
*TreeTransform
<Derived
>::TransformOMPWriteClause(OMPWriteClause
*C
) {
10453 // No need to rebuild this clause, no template-dependent parameters.
10457 template <typename Derived
>
10459 TreeTransform
<Derived
>::TransformOMPUpdateClause(OMPUpdateClause
*C
) {
10460 // No need to rebuild this clause, no template-dependent parameters.
10464 template <typename Derived
>
10466 TreeTransform
<Derived
>::TransformOMPCaptureClause(OMPCaptureClause
*C
) {
10467 // No need to rebuild this clause, no template-dependent parameters.
10471 template <typename Derived
>
10473 TreeTransform
<Derived
>::TransformOMPCompareClause(OMPCompareClause
*C
) {
10474 // No need to rebuild this clause, no template-dependent parameters.
10478 template <typename Derived
>
10479 OMPClause
*TreeTransform
<Derived
>::TransformOMPFailClause(OMPFailClause
*C
) {
10480 // No need to rebuild this clause, no template-dependent parameters.
10484 template <typename Derived
>
10486 TreeTransform
<Derived
>::TransformOMPAbsentClause(OMPAbsentClause
*C
) {
10490 template <typename Derived
>
10491 OMPClause
*TreeTransform
<Derived
>::TransformOMPHoldsClause(OMPHoldsClause
*C
) {
10492 ExprResult E
= getDerived().TransformExpr(C
->getExpr());
10495 return getDerived().RebuildOMPHoldsClause(E
.get(), C
->getBeginLoc(),
10496 C
->getLParenLoc(), C
->getEndLoc());
10499 template <typename Derived
>
10501 TreeTransform
<Derived
>::TransformOMPContainsClause(OMPContainsClause
*C
) {
10505 template <typename Derived
>
10507 TreeTransform
<Derived
>::TransformOMPNoOpenMPClause(OMPNoOpenMPClause
*C
) {
10510 template <typename Derived
>
10511 OMPClause
*TreeTransform
<Derived
>::TransformOMPNoOpenMPRoutinesClause(
10512 OMPNoOpenMPRoutinesClause
*C
) {
10515 template <typename Derived
>
10516 OMPClause
*TreeTransform
<Derived
>::TransformOMPNoParallelismClause(
10517 OMPNoParallelismClause
*C
) {
10521 template <typename Derived
>
10523 TreeTransform
<Derived
>::TransformOMPSeqCstClause(OMPSeqCstClause
*C
) {
10524 // No need to rebuild this clause, no template-dependent parameters.
10528 template <typename Derived
>
10530 TreeTransform
<Derived
>::TransformOMPAcqRelClause(OMPAcqRelClause
*C
) {
10531 // No need to rebuild this clause, no template-dependent parameters.
10535 template <typename Derived
>
10537 TreeTransform
<Derived
>::TransformOMPAcquireClause(OMPAcquireClause
*C
) {
10538 // No need to rebuild this clause, no template-dependent parameters.
10542 template <typename Derived
>
10544 TreeTransform
<Derived
>::TransformOMPReleaseClause(OMPReleaseClause
*C
) {
10545 // No need to rebuild this clause, no template-dependent parameters.
10549 template <typename Derived
>
10551 TreeTransform
<Derived
>::TransformOMPRelaxedClause(OMPRelaxedClause
*C
) {
10552 // No need to rebuild this clause, no template-dependent parameters.
10556 template <typename Derived
>
10557 OMPClause
*TreeTransform
<Derived
>::TransformOMPWeakClause(OMPWeakClause
*C
) {
10558 // No need to rebuild this clause, no template-dependent parameters.
10562 template <typename Derived
>
10564 TreeTransform
<Derived
>::TransformOMPThreadsClause(OMPThreadsClause
*C
) {
10565 // No need to rebuild this clause, no template-dependent parameters.
10569 template <typename Derived
>
10570 OMPClause
*TreeTransform
<Derived
>::TransformOMPSIMDClause(OMPSIMDClause
*C
) {
10571 // No need to rebuild this clause, no template-dependent parameters.
10575 template <typename Derived
>
10577 TreeTransform
<Derived
>::TransformOMPNogroupClause(OMPNogroupClause
*C
) {
10578 // No need to rebuild this clause, no template-dependent parameters.
10582 template <typename Derived
>
10583 OMPClause
*TreeTransform
<Derived
>::TransformOMPInitClause(OMPInitClause
*C
) {
10584 ExprResult IVR
= getDerived().TransformExpr(C
->getInteropVar());
10585 if (IVR
.isInvalid())
10588 OMPInteropInfo
InteropInfo(C
->getIsTarget(), C
->getIsTargetSync());
10589 InteropInfo
.PreferTypes
.reserve(C
->varlist_size() - 1);
10590 for (Expr
*E
: llvm::drop_begin(C
->varlist())) {
10591 ExprResult ER
= getDerived().TransformExpr(cast
<Expr
>(E
));
10592 if (ER
.isInvalid())
10594 InteropInfo
.PreferTypes
.push_back(ER
.get());
10596 return getDerived().RebuildOMPInitClause(IVR
.get(), InteropInfo
,
10597 C
->getBeginLoc(), C
->getLParenLoc(),
10598 C
->getVarLoc(), C
->getEndLoc());
10601 template <typename Derived
>
10602 OMPClause
*TreeTransform
<Derived
>::TransformOMPUseClause(OMPUseClause
*C
) {
10603 ExprResult ER
= getDerived().TransformExpr(C
->getInteropVar());
10604 if (ER
.isInvalid())
10606 return getDerived().RebuildOMPUseClause(ER
.get(), C
->getBeginLoc(),
10607 C
->getLParenLoc(), C
->getVarLoc(),
10611 template <typename Derived
>
10613 TreeTransform
<Derived
>::TransformOMPDestroyClause(OMPDestroyClause
*C
) {
10615 if (Expr
*IV
= C
->getInteropVar()) {
10616 ER
= getDerived().TransformExpr(IV
);
10617 if (ER
.isInvalid())
10620 return getDerived().RebuildOMPDestroyClause(ER
.get(), C
->getBeginLoc(),
10621 C
->getLParenLoc(), C
->getVarLoc(),
10625 template <typename Derived
>
10627 TreeTransform
<Derived
>::TransformOMPNovariantsClause(OMPNovariantsClause
*C
) {
10628 ExprResult Cond
= getDerived().TransformExpr(C
->getCondition());
10629 if (Cond
.isInvalid())
10631 return getDerived().RebuildOMPNovariantsClause(
10632 Cond
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10635 template <typename Derived
>
10637 TreeTransform
<Derived
>::TransformOMPNocontextClause(OMPNocontextClause
*C
) {
10638 ExprResult Cond
= getDerived().TransformExpr(C
->getCondition());
10639 if (Cond
.isInvalid())
10641 return getDerived().RebuildOMPNocontextClause(
10642 Cond
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10645 template <typename Derived
>
10647 TreeTransform
<Derived
>::TransformOMPFilterClause(OMPFilterClause
*C
) {
10648 ExprResult ThreadID
= getDerived().TransformExpr(C
->getThreadID());
10649 if (ThreadID
.isInvalid())
10651 return getDerived().RebuildOMPFilterClause(ThreadID
.get(), C
->getBeginLoc(),
10652 C
->getLParenLoc(), C
->getEndLoc());
10655 template <typename Derived
>
10656 OMPClause
*TreeTransform
<Derived
>::TransformOMPAlignClause(OMPAlignClause
*C
) {
10657 ExprResult E
= getDerived().TransformExpr(C
->getAlignment());
10660 return getDerived().RebuildOMPAlignClause(E
.get(), C
->getBeginLoc(),
10661 C
->getLParenLoc(), C
->getEndLoc());
10664 template <typename Derived
>
10665 OMPClause
*TreeTransform
<Derived
>::TransformOMPUnifiedAddressClause(
10666 OMPUnifiedAddressClause
*C
) {
10667 llvm_unreachable("unified_address clause cannot appear in dependent context");
10670 template <typename Derived
>
10671 OMPClause
*TreeTransform
<Derived
>::TransformOMPUnifiedSharedMemoryClause(
10672 OMPUnifiedSharedMemoryClause
*C
) {
10674 "unified_shared_memory clause cannot appear in dependent context");
10677 template <typename Derived
>
10678 OMPClause
*TreeTransform
<Derived
>::TransformOMPReverseOffloadClause(
10679 OMPReverseOffloadClause
*C
) {
10680 llvm_unreachable("reverse_offload clause cannot appear in dependent context");
10683 template <typename Derived
>
10684 OMPClause
*TreeTransform
<Derived
>::TransformOMPDynamicAllocatorsClause(
10685 OMPDynamicAllocatorsClause
*C
) {
10687 "dynamic_allocators clause cannot appear in dependent context");
10690 template <typename Derived
>
10691 OMPClause
*TreeTransform
<Derived
>::TransformOMPAtomicDefaultMemOrderClause(
10692 OMPAtomicDefaultMemOrderClause
*C
) {
10694 "atomic_default_mem_order clause cannot appear in dependent context");
10697 template <typename Derived
>
10698 OMPClause
*TreeTransform
<Derived
>::TransformOMPAtClause(OMPAtClause
*C
) {
10699 return getDerived().RebuildOMPAtClause(C
->getAtKind(), C
->getAtKindKwLoc(),
10700 C
->getBeginLoc(), C
->getLParenLoc(),
10704 template <typename Derived
>
10706 TreeTransform
<Derived
>::TransformOMPSeverityClause(OMPSeverityClause
*C
) {
10707 return getDerived().RebuildOMPSeverityClause(
10708 C
->getSeverityKind(), C
->getSeverityKindKwLoc(), C
->getBeginLoc(),
10709 C
->getLParenLoc(), C
->getEndLoc());
10712 template <typename Derived
>
10714 TreeTransform
<Derived
>::TransformOMPMessageClause(OMPMessageClause
*C
) {
10715 ExprResult E
= getDerived().TransformExpr(C
->getMessageString());
10718 return getDerived().RebuildOMPMessageClause(
10719 C
->getMessageString(), C
->getBeginLoc(), C
->getLParenLoc(),
10723 template <typename Derived
>
10725 TreeTransform
<Derived
>::TransformOMPPrivateClause(OMPPrivateClause
*C
) {
10726 llvm::SmallVector
<Expr
*, 16> Vars
;
10727 Vars
.reserve(C
->varlist_size());
10728 for (auto *VE
: C
->varlist()) {
10729 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10730 if (EVar
.isInvalid())
10732 Vars
.push_back(EVar
.get());
10734 return getDerived().RebuildOMPPrivateClause(
10735 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10738 template <typename Derived
>
10739 OMPClause
*TreeTransform
<Derived
>::TransformOMPFirstprivateClause(
10740 OMPFirstprivateClause
*C
) {
10741 llvm::SmallVector
<Expr
*, 16> Vars
;
10742 Vars
.reserve(C
->varlist_size());
10743 for (auto *VE
: C
->varlist()) {
10744 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10745 if (EVar
.isInvalid())
10747 Vars
.push_back(EVar
.get());
10749 return getDerived().RebuildOMPFirstprivateClause(
10750 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10753 template <typename Derived
>
10755 TreeTransform
<Derived
>::TransformOMPLastprivateClause(OMPLastprivateClause
*C
) {
10756 llvm::SmallVector
<Expr
*, 16> Vars
;
10757 Vars
.reserve(C
->varlist_size());
10758 for (auto *VE
: C
->varlist()) {
10759 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10760 if (EVar
.isInvalid())
10762 Vars
.push_back(EVar
.get());
10764 return getDerived().RebuildOMPLastprivateClause(
10765 Vars
, C
->getKind(), C
->getKindLoc(), C
->getColonLoc(), C
->getBeginLoc(),
10766 C
->getLParenLoc(), C
->getEndLoc());
10769 template <typename Derived
>
10771 TreeTransform
<Derived
>::TransformOMPSharedClause(OMPSharedClause
*C
) {
10772 llvm::SmallVector
<Expr
*, 16> Vars
;
10773 Vars
.reserve(C
->varlist_size());
10774 for (auto *VE
: C
->varlist()) {
10775 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10776 if (EVar
.isInvalid())
10778 Vars
.push_back(EVar
.get());
10780 return getDerived().RebuildOMPSharedClause(Vars
, C
->getBeginLoc(),
10781 C
->getLParenLoc(), C
->getEndLoc());
10784 template <typename Derived
>
10786 TreeTransform
<Derived
>::TransformOMPReductionClause(OMPReductionClause
*C
) {
10787 llvm::SmallVector
<Expr
*, 16> Vars
;
10788 Vars
.reserve(C
->varlist_size());
10789 for (auto *VE
: C
->varlist()) {
10790 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10791 if (EVar
.isInvalid())
10793 Vars
.push_back(EVar
.get());
10795 CXXScopeSpec ReductionIdScopeSpec
;
10796 ReductionIdScopeSpec
.Adopt(C
->getQualifierLoc());
10798 DeclarationNameInfo NameInfo
= C
->getNameInfo();
10799 if (NameInfo
.getName()) {
10800 NameInfo
= getDerived().TransformDeclarationNameInfo(NameInfo
);
10801 if (!NameInfo
.getName())
10804 // Build a list of all UDR decls with the same names ranged by the Scopes.
10805 // The Scope boundary is a duplication of the previous decl.
10806 llvm::SmallVector
<Expr
*, 16> UnresolvedReductions
;
10807 for (auto *E
: C
->reduction_ops()) {
10808 // Transform all the decls.
10810 auto *ULE
= cast
<UnresolvedLookupExpr
>(E
);
10811 UnresolvedSet
<8> Decls
;
10812 for (auto *D
: ULE
->decls()) {
10814 cast
<NamedDecl
>(getDerived().TransformDecl(E
->getExprLoc(), D
));
10815 Decls
.addDecl(InstD
, InstD
->getAccess());
10817 UnresolvedReductions
.push_back(UnresolvedLookupExpr::Create(
10818 SemaRef
.Context
, /*NamingClass=*/nullptr,
10819 ReductionIdScopeSpec
.getWithLocInContext(SemaRef
.Context
), NameInfo
,
10820 /*ADL=*/true, Decls
.begin(), Decls
.end(),
10821 /*KnownDependent=*/false, /*KnownInstantiationDependent=*/false));
10823 UnresolvedReductions
.push_back(nullptr);
10825 return getDerived().RebuildOMPReductionClause(
10826 Vars
, C
->getModifier(), C
->getBeginLoc(), C
->getLParenLoc(),
10827 C
->getModifierLoc(), C
->getColonLoc(), C
->getEndLoc(),
10828 ReductionIdScopeSpec
, NameInfo
, UnresolvedReductions
);
10831 template <typename Derived
>
10832 OMPClause
*TreeTransform
<Derived
>::TransformOMPTaskReductionClause(
10833 OMPTaskReductionClause
*C
) {
10834 llvm::SmallVector
<Expr
*, 16> Vars
;
10835 Vars
.reserve(C
->varlist_size());
10836 for (auto *VE
: C
->varlist()) {
10837 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10838 if (EVar
.isInvalid())
10840 Vars
.push_back(EVar
.get());
10842 CXXScopeSpec ReductionIdScopeSpec
;
10843 ReductionIdScopeSpec
.Adopt(C
->getQualifierLoc());
10845 DeclarationNameInfo NameInfo
= C
->getNameInfo();
10846 if (NameInfo
.getName()) {
10847 NameInfo
= getDerived().TransformDeclarationNameInfo(NameInfo
);
10848 if (!NameInfo
.getName())
10851 // Build a list of all UDR decls with the same names ranged by the Scopes.
10852 // The Scope boundary is a duplication of the previous decl.
10853 llvm::SmallVector
<Expr
*, 16> UnresolvedReductions
;
10854 for (auto *E
: C
->reduction_ops()) {
10855 // Transform all the decls.
10857 auto *ULE
= cast
<UnresolvedLookupExpr
>(E
);
10858 UnresolvedSet
<8> Decls
;
10859 for (auto *D
: ULE
->decls()) {
10861 cast
<NamedDecl
>(getDerived().TransformDecl(E
->getExprLoc(), D
));
10862 Decls
.addDecl(InstD
, InstD
->getAccess());
10864 UnresolvedReductions
.push_back(UnresolvedLookupExpr::Create(
10865 SemaRef
.Context
, /*NamingClass=*/nullptr,
10866 ReductionIdScopeSpec
.getWithLocInContext(SemaRef
.Context
), NameInfo
,
10867 /*ADL=*/true, Decls
.begin(), Decls
.end(),
10868 /*KnownDependent=*/false, /*KnownInstantiationDependent=*/false));
10870 UnresolvedReductions
.push_back(nullptr);
10872 return getDerived().RebuildOMPTaskReductionClause(
10873 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getColonLoc(),
10874 C
->getEndLoc(), ReductionIdScopeSpec
, NameInfo
, UnresolvedReductions
);
10877 template <typename Derived
>
10879 TreeTransform
<Derived
>::TransformOMPInReductionClause(OMPInReductionClause
*C
) {
10880 llvm::SmallVector
<Expr
*, 16> Vars
;
10881 Vars
.reserve(C
->varlist_size());
10882 for (auto *VE
: C
->varlist()) {
10883 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10884 if (EVar
.isInvalid())
10886 Vars
.push_back(EVar
.get());
10888 CXXScopeSpec ReductionIdScopeSpec
;
10889 ReductionIdScopeSpec
.Adopt(C
->getQualifierLoc());
10891 DeclarationNameInfo NameInfo
= C
->getNameInfo();
10892 if (NameInfo
.getName()) {
10893 NameInfo
= getDerived().TransformDeclarationNameInfo(NameInfo
);
10894 if (!NameInfo
.getName())
10897 // Build a list of all UDR decls with the same names ranged by the Scopes.
10898 // The Scope boundary is a duplication of the previous decl.
10899 llvm::SmallVector
<Expr
*, 16> UnresolvedReductions
;
10900 for (auto *E
: C
->reduction_ops()) {
10901 // Transform all the decls.
10903 auto *ULE
= cast
<UnresolvedLookupExpr
>(E
);
10904 UnresolvedSet
<8> Decls
;
10905 for (auto *D
: ULE
->decls()) {
10907 cast
<NamedDecl
>(getDerived().TransformDecl(E
->getExprLoc(), D
));
10908 Decls
.addDecl(InstD
, InstD
->getAccess());
10910 UnresolvedReductions
.push_back(UnresolvedLookupExpr::Create(
10911 SemaRef
.Context
, /*NamingClass=*/nullptr,
10912 ReductionIdScopeSpec
.getWithLocInContext(SemaRef
.Context
), NameInfo
,
10913 /*ADL=*/true, Decls
.begin(), Decls
.end(),
10914 /*KnownDependent=*/false, /*KnownInstantiationDependent=*/false));
10916 UnresolvedReductions
.push_back(nullptr);
10918 return getDerived().RebuildOMPInReductionClause(
10919 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getColonLoc(),
10920 C
->getEndLoc(), ReductionIdScopeSpec
, NameInfo
, UnresolvedReductions
);
10923 template <typename Derived
>
10925 TreeTransform
<Derived
>::TransformOMPLinearClause(OMPLinearClause
*C
) {
10926 llvm::SmallVector
<Expr
*, 16> Vars
;
10927 Vars
.reserve(C
->varlist_size());
10928 for (auto *VE
: C
->varlist()) {
10929 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10930 if (EVar
.isInvalid())
10932 Vars
.push_back(EVar
.get());
10934 ExprResult Step
= getDerived().TransformExpr(C
->getStep());
10935 if (Step
.isInvalid())
10937 return getDerived().RebuildOMPLinearClause(
10938 Vars
, Step
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getModifier(),
10939 C
->getModifierLoc(), C
->getColonLoc(), C
->getStepModifierLoc(),
10943 template <typename Derived
>
10945 TreeTransform
<Derived
>::TransformOMPAlignedClause(OMPAlignedClause
*C
) {
10946 llvm::SmallVector
<Expr
*, 16> Vars
;
10947 Vars
.reserve(C
->varlist_size());
10948 for (auto *VE
: C
->varlist()) {
10949 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10950 if (EVar
.isInvalid())
10952 Vars
.push_back(EVar
.get());
10954 ExprResult Alignment
= getDerived().TransformExpr(C
->getAlignment());
10955 if (Alignment
.isInvalid())
10957 return getDerived().RebuildOMPAlignedClause(
10958 Vars
, Alignment
.get(), C
->getBeginLoc(), C
->getLParenLoc(),
10959 C
->getColonLoc(), C
->getEndLoc());
10962 template <typename Derived
>
10964 TreeTransform
<Derived
>::TransformOMPCopyinClause(OMPCopyinClause
*C
) {
10965 llvm::SmallVector
<Expr
*, 16> Vars
;
10966 Vars
.reserve(C
->varlist_size());
10967 for (auto *VE
: C
->varlist()) {
10968 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10969 if (EVar
.isInvalid())
10971 Vars
.push_back(EVar
.get());
10973 return getDerived().RebuildOMPCopyinClause(Vars
, C
->getBeginLoc(),
10974 C
->getLParenLoc(), C
->getEndLoc());
10977 template <typename Derived
>
10979 TreeTransform
<Derived
>::TransformOMPCopyprivateClause(OMPCopyprivateClause
*C
) {
10980 llvm::SmallVector
<Expr
*, 16> Vars
;
10981 Vars
.reserve(C
->varlist_size());
10982 for (auto *VE
: C
->varlist()) {
10983 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10984 if (EVar
.isInvalid())
10986 Vars
.push_back(EVar
.get());
10988 return getDerived().RebuildOMPCopyprivateClause(
10989 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
10992 template <typename Derived
>
10993 OMPClause
*TreeTransform
<Derived
>::TransformOMPFlushClause(OMPFlushClause
*C
) {
10994 llvm::SmallVector
<Expr
*, 16> Vars
;
10995 Vars
.reserve(C
->varlist_size());
10996 for (auto *VE
: C
->varlist()) {
10997 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
10998 if (EVar
.isInvalid())
11000 Vars
.push_back(EVar
.get());
11002 return getDerived().RebuildOMPFlushClause(Vars
, C
->getBeginLoc(),
11003 C
->getLParenLoc(), C
->getEndLoc());
11006 template <typename Derived
>
11008 TreeTransform
<Derived
>::TransformOMPDepobjClause(OMPDepobjClause
*C
) {
11009 ExprResult E
= getDerived().TransformExpr(C
->getDepobj());
11012 return getDerived().RebuildOMPDepobjClause(E
.get(), C
->getBeginLoc(),
11013 C
->getLParenLoc(), C
->getEndLoc());
11016 template <typename Derived
>
11018 TreeTransform
<Derived
>::TransformOMPDependClause(OMPDependClause
*C
) {
11019 llvm::SmallVector
<Expr
*, 16> Vars
;
11020 Expr
*DepModifier
= C
->getModifier();
11022 ExprResult DepModRes
= getDerived().TransformExpr(DepModifier
);
11023 if (DepModRes
.isInvalid())
11025 DepModifier
= DepModRes
.get();
11027 Vars
.reserve(C
->varlist_size());
11028 for (auto *VE
: C
->varlist()) {
11029 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11030 if (EVar
.isInvalid())
11032 Vars
.push_back(EVar
.get());
11034 return getDerived().RebuildOMPDependClause(
11035 {C
->getDependencyKind(), C
->getDependencyLoc(), C
->getColonLoc(),
11036 C
->getOmpAllMemoryLoc()},
11037 DepModifier
, Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11040 template <typename Derived
>
11042 TreeTransform
<Derived
>::TransformOMPDeviceClause(OMPDeviceClause
*C
) {
11043 ExprResult E
= getDerived().TransformExpr(C
->getDevice());
11046 return getDerived().RebuildOMPDeviceClause(
11047 C
->getModifier(), E
.get(), C
->getBeginLoc(), C
->getLParenLoc(),
11048 C
->getModifierLoc(), C
->getEndLoc());
11051 template <typename Derived
, class T
>
11052 bool transformOMPMappableExprListClause(
11053 TreeTransform
<Derived
> &TT
, OMPMappableExprListClause
<T
> *C
,
11054 llvm::SmallVectorImpl
<Expr
*> &Vars
, CXXScopeSpec
&MapperIdScopeSpec
,
11055 DeclarationNameInfo
&MapperIdInfo
,
11056 llvm::SmallVectorImpl
<Expr
*> &UnresolvedMappers
) {
11057 // Transform expressions in the list.
11058 Vars
.reserve(C
->varlist_size());
11059 for (auto *VE
: C
->varlist()) {
11060 ExprResult EVar
= TT
.getDerived().TransformExpr(cast
<Expr
>(VE
));
11061 if (EVar
.isInvalid())
11063 Vars
.push_back(EVar
.get());
11065 // Transform mapper scope specifier and identifier.
11066 NestedNameSpecifierLoc QualifierLoc
;
11067 if (C
->getMapperQualifierLoc()) {
11068 QualifierLoc
= TT
.getDerived().TransformNestedNameSpecifierLoc(
11069 C
->getMapperQualifierLoc());
11073 MapperIdScopeSpec
.Adopt(QualifierLoc
);
11074 MapperIdInfo
= C
->getMapperIdInfo();
11075 if (MapperIdInfo
.getName()) {
11076 MapperIdInfo
= TT
.getDerived().TransformDeclarationNameInfo(MapperIdInfo
);
11077 if (!MapperIdInfo
.getName())
11080 // Build a list of all candidate OMPDeclareMapperDecls, which is provided by
11081 // the previous user-defined mapper lookup in dependent environment.
11082 for (auto *E
: C
->mapperlists()) {
11083 // Transform all the decls.
11085 auto *ULE
= cast
<UnresolvedLookupExpr
>(E
);
11086 UnresolvedSet
<8> Decls
;
11087 for (auto *D
: ULE
->decls()) {
11089 cast
<NamedDecl
>(TT
.getDerived().TransformDecl(E
->getExprLoc(), D
));
11090 Decls
.addDecl(InstD
, InstD
->getAccess());
11092 UnresolvedMappers
.push_back(UnresolvedLookupExpr::Create(
11093 TT
.getSema().Context
, /*NamingClass=*/nullptr,
11094 MapperIdScopeSpec
.getWithLocInContext(TT
.getSema().Context
),
11095 MapperIdInfo
, /*ADL=*/true, Decls
.begin(), Decls
.end(),
11096 /*KnownDependent=*/false, /*KnownInstantiationDependent=*/false));
11098 UnresolvedMappers
.push_back(nullptr);
11104 template <typename Derived
>
11105 OMPClause
*TreeTransform
<Derived
>::TransformOMPMapClause(OMPMapClause
*C
) {
11106 OMPVarListLocTy
Locs(C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11107 llvm::SmallVector
<Expr
*, 16> Vars
;
11108 Expr
*IteratorModifier
= C
->getIteratorModifier();
11109 if (IteratorModifier
) {
11110 ExprResult MapModRes
= getDerived().TransformExpr(IteratorModifier
);
11111 if (MapModRes
.isInvalid())
11113 IteratorModifier
= MapModRes
.get();
11115 CXXScopeSpec MapperIdScopeSpec
;
11116 DeclarationNameInfo MapperIdInfo
;
11117 llvm::SmallVector
<Expr
*, 16> UnresolvedMappers
;
11118 if (transformOMPMappableExprListClause
<Derived
, OMPMapClause
>(
11119 *this, C
, Vars
, MapperIdScopeSpec
, MapperIdInfo
, UnresolvedMappers
))
11121 return getDerived().RebuildOMPMapClause(
11122 IteratorModifier
, C
->getMapTypeModifiers(), C
->getMapTypeModifiersLoc(),
11123 MapperIdScopeSpec
, MapperIdInfo
, C
->getMapType(), C
->isImplicitMapType(),
11124 C
->getMapLoc(), C
->getColonLoc(), Vars
, Locs
, UnresolvedMappers
);
11127 template <typename Derived
>
11129 TreeTransform
<Derived
>::TransformOMPAllocateClause(OMPAllocateClause
*C
) {
11130 Expr
*Allocator
= C
->getAllocator();
11132 ExprResult AllocatorRes
= getDerived().TransformExpr(Allocator
);
11133 if (AllocatorRes
.isInvalid())
11135 Allocator
= AllocatorRes
.get();
11137 llvm::SmallVector
<Expr
*, 16> Vars
;
11138 Vars
.reserve(C
->varlist_size());
11139 for (auto *VE
: C
->varlist()) {
11140 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11141 if (EVar
.isInvalid())
11143 Vars
.push_back(EVar
.get());
11145 return getDerived().RebuildOMPAllocateClause(
11146 Allocator
, C
->getAllocatorModifier(), Vars
, C
->getBeginLoc(),
11147 C
->getLParenLoc(), C
->getColonLoc(), C
->getEndLoc());
11150 template <typename Derived
>
11152 TreeTransform
<Derived
>::TransformOMPNumTeamsClause(OMPNumTeamsClause
*C
) {
11153 llvm::SmallVector
<Expr
*, 3> Vars
;
11154 Vars
.reserve(C
->varlist_size());
11155 for (auto *VE
: C
->varlist()) {
11156 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11157 if (EVar
.isInvalid())
11159 Vars
.push_back(EVar
.get());
11161 return getDerived().RebuildOMPNumTeamsClause(
11162 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11165 template <typename Derived
>
11167 TreeTransform
<Derived
>::TransformOMPThreadLimitClause(OMPThreadLimitClause
*C
) {
11168 llvm::SmallVector
<Expr
*, 3> Vars
;
11169 Vars
.reserve(C
->varlist_size());
11170 for (auto *VE
: C
->varlist()) {
11171 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11172 if (EVar
.isInvalid())
11174 Vars
.push_back(EVar
.get());
11176 return getDerived().RebuildOMPThreadLimitClause(
11177 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11180 template <typename Derived
>
11182 TreeTransform
<Derived
>::TransformOMPPriorityClause(OMPPriorityClause
*C
) {
11183 ExprResult E
= getDerived().TransformExpr(C
->getPriority());
11186 return getDerived().RebuildOMPPriorityClause(
11187 E
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11190 template <typename Derived
>
11192 TreeTransform
<Derived
>::TransformOMPGrainsizeClause(OMPGrainsizeClause
*C
) {
11193 ExprResult E
= getDerived().TransformExpr(C
->getGrainsize());
11196 return getDerived().RebuildOMPGrainsizeClause(
11197 C
->getModifier(), E
.get(), C
->getBeginLoc(), C
->getLParenLoc(),
11198 C
->getModifierLoc(), C
->getEndLoc());
11201 template <typename Derived
>
11203 TreeTransform
<Derived
>::TransformOMPNumTasksClause(OMPNumTasksClause
*C
) {
11204 ExprResult E
= getDerived().TransformExpr(C
->getNumTasks());
11207 return getDerived().RebuildOMPNumTasksClause(
11208 C
->getModifier(), E
.get(), C
->getBeginLoc(), C
->getLParenLoc(),
11209 C
->getModifierLoc(), C
->getEndLoc());
11212 template <typename Derived
>
11213 OMPClause
*TreeTransform
<Derived
>::TransformOMPHintClause(OMPHintClause
*C
) {
11214 ExprResult E
= getDerived().TransformExpr(C
->getHint());
11217 return getDerived().RebuildOMPHintClause(E
.get(), C
->getBeginLoc(),
11218 C
->getLParenLoc(), C
->getEndLoc());
11221 template <typename Derived
>
11222 OMPClause
*TreeTransform
<Derived
>::TransformOMPDistScheduleClause(
11223 OMPDistScheduleClause
*C
) {
11224 ExprResult E
= getDerived().TransformExpr(C
->getChunkSize());
11227 return getDerived().RebuildOMPDistScheduleClause(
11228 C
->getDistScheduleKind(), E
.get(), C
->getBeginLoc(), C
->getLParenLoc(),
11229 C
->getDistScheduleKindLoc(), C
->getCommaLoc(), C
->getEndLoc());
11232 template <typename Derived
>
11234 TreeTransform
<Derived
>::TransformOMPDefaultmapClause(OMPDefaultmapClause
*C
) {
11235 // Rebuild Defaultmap Clause since we need to invoke the checking of
11236 // defaultmap(none:variable-category) after template initialization.
11237 return getDerived().RebuildOMPDefaultmapClause(C
->getDefaultmapModifier(),
11238 C
->getDefaultmapKind(),
11241 C
->getDefaultmapModifierLoc(),
11242 C
->getDefaultmapKindLoc(),
11246 template <typename Derived
>
11247 OMPClause
*TreeTransform
<Derived
>::TransformOMPToClause(OMPToClause
*C
) {
11248 OMPVarListLocTy
Locs(C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11249 llvm::SmallVector
<Expr
*, 16> Vars
;
11250 CXXScopeSpec MapperIdScopeSpec
;
11251 DeclarationNameInfo MapperIdInfo
;
11252 llvm::SmallVector
<Expr
*, 16> UnresolvedMappers
;
11253 if (transformOMPMappableExprListClause
<Derived
, OMPToClause
>(
11254 *this, C
, Vars
, MapperIdScopeSpec
, MapperIdInfo
, UnresolvedMappers
))
11256 return getDerived().RebuildOMPToClause(
11257 C
->getMotionModifiers(), C
->getMotionModifiersLoc(), MapperIdScopeSpec
,
11258 MapperIdInfo
, C
->getColonLoc(), Vars
, Locs
, UnresolvedMappers
);
11261 template <typename Derived
>
11262 OMPClause
*TreeTransform
<Derived
>::TransformOMPFromClause(OMPFromClause
*C
) {
11263 OMPVarListLocTy
Locs(C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11264 llvm::SmallVector
<Expr
*, 16> Vars
;
11265 CXXScopeSpec MapperIdScopeSpec
;
11266 DeclarationNameInfo MapperIdInfo
;
11267 llvm::SmallVector
<Expr
*, 16> UnresolvedMappers
;
11268 if (transformOMPMappableExprListClause
<Derived
, OMPFromClause
>(
11269 *this, C
, Vars
, MapperIdScopeSpec
, MapperIdInfo
, UnresolvedMappers
))
11271 return getDerived().RebuildOMPFromClause(
11272 C
->getMotionModifiers(), C
->getMotionModifiersLoc(), MapperIdScopeSpec
,
11273 MapperIdInfo
, C
->getColonLoc(), Vars
, Locs
, UnresolvedMappers
);
11276 template <typename Derived
>
11277 OMPClause
*TreeTransform
<Derived
>::TransformOMPUseDevicePtrClause(
11278 OMPUseDevicePtrClause
*C
) {
11279 llvm::SmallVector
<Expr
*, 16> Vars
;
11280 Vars
.reserve(C
->varlist_size());
11281 for (auto *VE
: C
->varlist()) {
11282 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11283 if (EVar
.isInvalid())
11285 Vars
.push_back(EVar
.get());
11287 OMPVarListLocTy
Locs(C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11288 return getDerived().RebuildOMPUseDevicePtrClause(Vars
, Locs
);
11291 template <typename Derived
>
11292 OMPClause
*TreeTransform
<Derived
>::TransformOMPUseDeviceAddrClause(
11293 OMPUseDeviceAddrClause
*C
) {
11294 llvm::SmallVector
<Expr
*, 16> Vars
;
11295 Vars
.reserve(C
->varlist_size());
11296 for (auto *VE
: C
->varlist()) {
11297 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11298 if (EVar
.isInvalid())
11300 Vars
.push_back(EVar
.get());
11302 OMPVarListLocTy
Locs(C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11303 return getDerived().RebuildOMPUseDeviceAddrClause(Vars
, Locs
);
11306 template <typename Derived
>
11308 TreeTransform
<Derived
>::TransformOMPIsDevicePtrClause(OMPIsDevicePtrClause
*C
) {
11309 llvm::SmallVector
<Expr
*, 16> Vars
;
11310 Vars
.reserve(C
->varlist_size());
11311 for (auto *VE
: C
->varlist()) {
11312 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11313 if (EVar
.isInvalid())
11315 Vars
.push_back(EVar
.get());
11317 OMPVarListLocTy
Locs(C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11318 return getDerived().RebuildOMPIsDevicePtrClause(Vars
, Locs
);
11321 template <typename Derived
>
11322 OMPClause
*TreeTransform
<Derived
>::TransformOMPHasDeviceAddrClause(
11323 OMPHasDeviceAddrClause
*C
) {
11324 llvm::SmallVector
<Expr
*, 16> Vars
;
11325 Vars
.reserve(C
->varlist_size());
11326 for (auto *VE
: C
->varlist()) {
11327 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11328 if (EVar
.isInvalid())
11330 Vars
.push_back(EVar
.get());
11332 OMPVarListLocTy
Locs(C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11333 return getDerived().RebuildOMPHasDeviceAddrClause(Vars
, Locs
);
11336 template <typename Derived
>
11338 TreeTransform
<Derived
>::TransformOMPNontemporalClause(OMPNontemporalClause
*C
) {
11339 llvm::SmallVector
<Expr
*, 16> Vars
;
11340 Vars
.reserve(C
->varlist_size());
11341 for (auto *VE
: C
->varlist()) {
11342 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11343 if (EVar
.isInvalid())
11345 Vars
.push_back(EVar
.get());
11347 return getDerived().RebuildOMPNontemporalClause(
11348 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11351 template <typename Derived
>
11353 TreeTransform
<Derived
>::TransformOMPInclusiveClause(OMPInclusiveClause
*C
) {
11354 llvm::SmallVector
<Expr
*, 16> Vars
;
11355 Vars
.reserve(C
->varlist_size());
11356 for (auto *VE
: C
->varlist()) {
11357 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11358 if (EVar
.isInvalid())
11360 Vars
.push_back(EVar
.get());
11362 return getDerived().RebuildOMPInclusiveClause(
11363 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11366 template <typename Derived
>
11368 TreeTransform
<Derived
>::TransformOMPExclusiveClause(OMPExclusiveClause
*C
) {
11369 llvm::SmallVector
<Expr
*, 16> Vars
;
11370 Vars
.reserve(C
->varlist_size());
11371 for (auto *VE
: C
->varlist()) {
11372 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11373 if (EVar
.isInvalid())
11375 Vars
.push_back(EVar
.get());
11377 return getDerived().RebuildOMPExclusiveClause(
11378 Vars
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11381 template <typename Derived
>
11382 OMPClause
*TreeTransform
<Derived
>::TransformOMPUsesAllocatorsClause(
11383 OMPUsesAllocatorsClause
*C
) {
11384 SmallVector
<SemaOpenMP::UsesAllocatorsData
, 16> Data
;
11385 Data
.reserve(C
->getNumberOfAllocators());
11386 for (unsigned I
= 0, E
= C
->getNumberOfAllocators(); I
< E
; ++I
) {
11387 OMPUsesAllocatorsClause::Data D
= C
->getAllocatorData(I
);
11388 ExprResult Allocator
= getDerived().TransformExpr(D
.Allocator
);
11389 if (Allocator
.isInvalid())
11391 ExprResult AllocatorTraits
;
11392 if (Expr
*AT
= D
.AllocatorTraits
) {
11393 AllocatorTraits
= getDerived().TransformExpr(AT
);
11394 if (AllocatorTraits
.isInvalid())
11397 SemaOpenMP::UsesAllocatorsData
&NewD
= Data
.emplace_back();
11398 NewD
.Allocator
= Allocator
.get();
11399 NewD
.AllocatorTraits
= AllocatorTraits
.get();
11400 NewD
.LParenLoc
= D
.LParenLoc
;
11401 NewD
.RParenLoc
= D
.RParenLoc
;
11403 return getDerived().RebuildOMPUsesAllocatorsClause(
11404 Data
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11407 template <typename Derived
>
11409 TreeTransform
<Derived
>::TransformOMPAffinityClause(OMPAffinityClause
*C
) {
11410 SmallVector
<Expr
*, 4> Locators
;
11411 Locators
.reserve(C
->varlist_size());
11412 ExprResult ModifierRes
;
11413 if (Expr
*Modifier
= C
->getModifier()) {
11414 ModifierRes
= getDerived().TransformExpr(Modifier
);
11415 if (ModifierRes
.isInvalid())
11418 for (Expr
*E
: C
->varlist()) {
11419 ExprResult Locator
= getDerived().TransformExpr(E
);
11420 if (Locator
.isInvalid())
11422 Locators
.push_back(Locator
.get());
11424 return getDerived().RebuildOMPAffinityClause(
11425 C
->getBeginLoc(), C
->getLParenLoc(), C
->getColonLoc(), C
->getEndLoc(),
11426 ModifierRes
.get(), Locators
);
11429 template <typename Derived
>
11430 OMPClause
*TreeTransform
<Derived
>::TransformOMPOrderClause(OMPOrderClause
*C
) {
11431 return getDerived().RebuildOMPOrderClause(
11432 C
->getKind(), C
->getKindKwLoc(), C
->getBeginLoc(), C
->getLParenLoc(),
11433 C
->getEndLoc(), C
->getModifier(), C
->getModifierKwLoc());
11436 template <typename Derived
>
11437 OMPClause
*TreeTransform
<Derived
>::TransformOMPBindClause(OMPBindClause
*C
) {
11438 return getDerived().RebuildOMPBindClause(
11439 C
->getBindKind(), C
->getBindKindLoc(), C
->getBeginLoc(),
11440 C
->getLParenLoc(), C
->getEndLoc());
11443 template <typename Derived
>
11444 OMPClause
*TreeTransform
<Derived
>::TransformOMPXDynCGroupMemClause(
11445 OMPXDynCGroupMemClause
*C
) {
11446 ExprResult Size
= getDerived().TransformExpr(C
->getSize());
11447 if (Size
.isInvalid())
11449 return getDerived().RebuildOMPXDynCGroupMemClause(
11450 Size
.get(), C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11453 template <typename Derived
>
11455 TreeTransform
<Derived
>::TransformOMPDoacrossClause(OMPDoacrossClause
*C
) {
11456 llvm::SmallVector
<Expr
*, 16> Vars
;
11457 Vars
.reserve(C
->varlist_size());
11458 for (auto *VE
: C
->varlist()) {
11459 ExprResult EVar
= getDerived().TransformExpr(cast
<Expr
>(VE
));
11460 if (EVar
.isInvalid())
11462 Vars
.push_back(EVar
.get());
11464 return getDerived().RebuildOMPDoacrossClause(
11465 C
->getDependenceType(), C
->getDependenceLoc(), C
->getColonLoc(), Vars
,
11466 C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11469 template <typename Derived
>
11471 TreeTransform
<Derived
>::TransformOMPXAttributeClause(OMPXAttributeClause
*C
) {
11472 SmallVector
<const Attr
*> NewAttrs
;
11473 for (auto *A
: C
->getAttrs())
11474 NewAttrs
.push_back(getDerived().TransformAttr(A
));
11475 return getDerived().RebuildOMPXAttributeClause(
11476 NewAttrs
, C
->getBeginLoc(), C
->getLParenLoc(), C
->getEndLoc());
11479 template <typename Derived
>
11480 OMPClause
*TreeTransform
<Derived
>::TransformOMPXBareClause(OMPXBareClause
*C
) {
11481 return getDerived().RebuildOMPXBareClause(C
->getBeginLoc(), C
->getEndLoc());
11484 //===----------------------------------------------------------------------===//
11485 // OpenACC transformation
11486 //===----------------------------------------------------------------------===//
11488 template <typename Derived
>
11489 class OpenACCClauseTransform final
11490 : public OpenACCClauseVisitor
<OpenACCClauseTransform
<Derived
>> {
11491 TreeTransform
<Derived
> &Self
;
11492 ArrayRef
<const OpenACCClause
*> ExistingClauses
;
11493 SemaOpenACC::OpenACCParsedClause
&ParsedClause
;
11494 OpenACCClause
*NewClause
= nullptr;
11496 llvm::SmallVector
<Expr
*> VisitVarList(ArrayRef
<Expr
*> VarList
) {
11497 llvm::SmallVector
<Expr
*> InstantiatedVarList
;
11498 for (Expr
*CurVar
: VarList
) {
11499 ExprResult Res
= Self
.TransformExpr(CurVar
);
11501 if (!Res
.isUsable())
11504 Res
= Self
.getSema().OpenACC().ActOnVar(ParsedClause
.getClauseKind(),
11507 if (Res
.isUsable())
11508 InstantiatedVarList
.push_back(Res
.get());
11511 return InstantiatedVarList
;
11515 OpenACCClauseTransform(TreeTransform
<Derived
> &Self
,
11516 ArrayRef
<const OpenACCClause
*> ExistingClauses
,
11517 SemaOpenACC::OpenACCParsedClause
&PC
)
11518 : Self(Self
), ExistingClauses(ExistingClauses
), ParsedClause(PC
) {}
11520 OpenACCClause
*CreatedClause() const { return NewClause
; }
11522 #define VISIT_CLAUSE(CLAUSE_NAME) \
11523 void Visit##CLAUSE_NAME##Clause(const OpenACC##CLAUSE_NAME##Clause &Clause);
11524 #include "clang/Basic/OpenACCClauses.def"
11527 template <typename Derived
>
11528 void OpenACCClauseTransform
<Derived
>::VisitDefaultClause(
11529 const OpenACCDefaultClause
&C
) {
11530 ParsedClause
.setDefaultDetails(C
.getDefaultClauseKind());
11532 NewClause
= OpenACCDefaultClause::Create(
11533 Self
.getSema().getASTContext(), ParsedClause
.getDefaultClauseKind(),
11534 ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
11535 ParsedClause
.getEndLoc());
11538 template <typename Derived
>
11539 void OpenACCClauseTransform
<Derived
>::VisitIfClause(const OpenACCIfClause
&C
) {
11540 Expr
*Cond
= const_cast<Expr
*>(C
.getConditionExpr());
11541 assert(Cond
&& "If constructed with invalid Condition");
11542 Sema::ConditionResult Res
= Self
.TransformCondition(
11543 Cond
->getExprLoc(), /*Var=*/nullptr, Cond
, Sema::ConditionKind::Boolean
);
11545 if (Res
.isInvalid() || !Res
.get().second
)
11548 ParsedClause
.setConditionDetails(Res
.get().second
);
11550 NewClause
= OpenACCIfClause::Create(
11551 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11552 ParsedClause
.getLParenLoc(), ParsedClause
.getConditionExpr(),
11553 ParsedClause
.getEndLoc());
11556 template <typename Derived
>
11557 void OpenACCClauseTransform
<Derived
>::VisitSelfClause(
11558 const OpenACCSelfClause
&C
) {
11560 if (C
.hasConditionExpr()) {
11561 Expr
*Cond
= const_cast<Expr
*>(C
.getConditionExpr());
11562 Sema::ConditionResult Res
=
11563 Self
.TransformCondition(Cond
->getExprLoc(), /*Var=*/nullptr, Cond
,
11564 Sema::ConditionKind::Boolean
);
11566 if (Res
.isInvalid() || !Res
.get().second
)
11569 ParsedClause
.setConditionDetails(Res
.get().second
);
11572 NewClause
= OpenACCSelfClause::Create(
11573 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11574 ParsedClause
.getLParenLoc(), ParsedClause
.getConditionExpr(),
11575 ParsedClause
.getEndLoc());
11578 template <typename Derived
>
11579 void OpenACCClauseTransform
<Derived
>::VisitNumGangsClause(
11580 const OpenACCNumGangsClause
&C
) {
11581 llvm::SmallVector
<Expr
*> InstantiatedIntExprs
;
11583 for (Expr
*CurIntExpr
: C
.getIntExprs()) {
11584 ExprResult Res
= Self
.TransformExpr(CurIntExpr
);
11586 if (!Res
.isUsable())
11589 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11591 C
.getBeginLoc(), Res
.get());
11592 if (!Res
.isUsable())
11595 InstantiatedIntExprs
.push_back(Res
.get());
11598 ParsedClause
.setIntExprDetails(InstantiatedIntExprs
);
11599 NewClause
= OpenACCNumGangsClause::Create(
11600 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11601 ParsedClause
.getLParenLoc(), ParsedClause
.getIntExprs(),
11602 ParsedClause
.getEndLoc());
11605 template <typename Derived
>
11606 void OpenACCClauseTransform
<Derived
>::VisitPrivateClause(
11607 const OpenACCPrivateClause
&C
) {
11608 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()),
11609 /*IsReadOnly=*/false, /*IsZero=*/false);
11611 NewClause
= OpenACCPrivateClause::Create(
11612 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11613 ParsedClause
.getLParenLoc(), ParsedClause
.getVarList(),
11614 ParsedClause
.getEndLoc());
11617 template <typename Derived
>
11618 void OpenACCClauseTransform
<Derived
>::VisitFirstPrivateClause(
11619 const OpenACCFirstPrivateClause
&C
) {
11620 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()),
11621 /*IsReadOnly=*/false, /*IsZero=*/false);
11623 NewClause
= OpenACCFirstPrivateClause::Create(
11624 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11625 ParsedClause
.getLParenLoc(), ParsedClause
.getVarList(),
11626 ParsedClause
.getEndLoc());
11629 template <typename Derived
>
11630 void OpenACCClauseTransform
<Derived
>::VisitNoCreateClause(
11631 const OpenACCNoCreateClause
&C
) {
11632 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()),
11633 /*IsReadOnly=*/false, /*IsZero=*/false);
11635 NewClause
= OpenACCNoCreateClause::Create(
11636 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11637 ParsedClause
.getLParenLoc(), ParsedClause
.getVarList(),
11638 ParsedClause
.getEndLoc());
11641 template <typename Derived
>
11642 void OpenACCClauseTransform
<Derived
>::VisitPresentClause(
11643 const OpenACCPresentClause
&C
) {
11644 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()),
11645 /*IsReadOnly=*/false, /*IsZero=*/false);
11647 NewClause
= OpenACCPresentClause::Create(
11648 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11649 ParsedClause
.getLParenLoc(), ParsedClause
.getVarList(),
11650 ParsedClause
.getEndLoc());
11653 template <typename Derived
>
11654 void OpenACCClauseTransform
<Derived
>::VisitCopyClause(
11655 const OpenACCCopyClause
&C
) {
11656 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()),
11657 /*IsReadOnly=*/false, /*IsZero=*/false);
11659 NewClause
= OpenACCCopyClause::Create(
11660 Self
.getSema().getASTContext(), ParsedClause
.getClauseKind(),
11661 ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
11662 ParsedClause
.getVarList(), ParsedClause
.getEndLoc());
11665 template <typename Derived
>
11666 void OpenACCClauseTransform
<Derived
>::VisitCopyInClause(
11667 const OpenACCCopyInClause
&C
) {
11668 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()), C
.isReadOnly(),
11671 NewClause
= OpenACCCopyInClause::Create(
11672 Self
.getSema().getASTContext(), ParsedClause
.getClauseKind(),
11673 ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
11674 ParsedClause
.isReadOnly(), ParsedClause
.getVarList(),
11675 ParsedClause
.getEndLoc());
11678 template <typename Derived
>
11679 void OpenACCClauseTransform
<Derived
>::VisitCopyOutClause(
11680 const OpenACCCopyOutClause
&C
) {
11681 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()),
11682 /*IsReadOnly=*/false, C
.isZero());
11684 NewClause
= OpenACCCopyOutClause::Create(
11685 Self
.getSema().getASTContext(), ParsedClause
.getClauseKind(),
11686 ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
11687 ParsedClause
.isZero(), ParsedClause
.getVarList(),
11688 ParsedClause
.getEndLoc());
11691 template <typename Derived
>
11692 void OpenACCClauseTransform
<Derived
>::VisitCreateClause(
11693 const OpenACCCreateClause
&C
) {
11694 ParsedClause
.setVarListDetails(VisitVarList(C
.getVarList()),
11695 /*IsReadOnly=*/false, C
.isZero());
11697 NewClause
= OpenACCCreateClause::Create(
11698 Self
.getSema().getASTContext(), ParsedClause
.getClauseKind(),
11699 ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
11700 ParsedClause
.isZero(), ParsedClause
.getVarList(),
11701 ParsedClause
.getEndLoc());
11703 template <typename Derived
>
11704 void OpenACCClauseTransform
<Derived
>::VisitAttachClause(
11705 const OpenACCAttachClause
&C
) {
11706 llvm::SmallVector
<Expr
*> VarList
= VisitVarList(C
.getVarList());
11708 // Ensure each var is a pointer type.
11709 VarList
.erase(std::remove_if(VarList
.begin(), VarList
.end(), [&](Expr
*E
) {
11710 return Self
.getSema().OpenACC().CheckVarIsPointerType(
11711 OpenACCClauseKind::Attach
, E
);
11712 }), VarList
.end());
11714 ParsedClause
.setVarListDetails(VarList
,
11715 /*IsReadOnly=*/false, /*IsZero=*/false);
11716 NewClause
= OpenACCAttachClause::Create(
11717 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11718 ParsedClause
.getLParenLoc(), ParsedClause
.getVarList(),
11719 ParsedClause
.getEndLoc());
11722 template <typename Derived
>
11723 void OpenACCClauseTransform
<Derived
>::VisitDevicePtrClause(
11724 const OpenACCDevicePtrClause
&C
) {
11725 llvm::SmallVector
<Expr
*> VarList
= VisitVarList(C
.getVarList());
11727 // Ensure each var is a pointer type.
11728 VarList
.erase(std::remove_if(VarList
.begin(), VarList
.end(), [&](Expr
*E
) {
11729 return Self
.getSema().OpenACC().CheckVarIsPointerType(
11730 OpenACCClauseKind::DevicePtr
, E
);
11731 }), VarList
.end());
11733 ParsedClause
.setVarListDetails(VarList
,
11734 /*IsReadOnly=*/false, /*IsZero=*/false);
11735 NewClause
= OpenACCDevicePtrClause::Create(
11736 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11737 ParsedClause
.getLParenLoc(), ParsedClause
.getVarList(),
11738 ParsedClause
.getEndLoc());
11741 template <typename Derived
>
11742 void OpenACCClauseTransform
<Derived
>::VisitNumWorkersClause(
11743 const OpenACCNumWorkersClause
&C
) {
11744 Expr
*IntExpr
= const_cast<Expr
*>(C
.getIntExpr());
11745 assert(IntExpr
&& "num_workers clause constructed with invalid int expr");
11747 ExprResult Res
= Self
.TransformExpr(IntExpr
);
11748 if (!Res
.isUsable())
11751 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11753 C
.getBeginLoc(), Res
.get());
11754 if (!Res
.isUsable())
11757 ParsedClause
.setIntExprDetails(Res
.get());
11758 NewClause
= OpenACCNumWorkersClause::Create(
11759 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11760 ParsedClause
.getLParenLoc(), ParsedClause
.getIntExprs()[0],
11761 ParsedClause
.getEndLoc());
11764 template <typename Derived
>
11765 void OpenACCClauseTransform
<Derived
>::VisitVectorLengthClause(
11766 const OpenACCVectorLengthClause
&C
) {
11767 Expr
*IntExpr
= const_cast<Expr
*>(C
.getIntExpr());
11768 assert(IntExpr
&& "vector_length clause constructed with invalid int expr");
11770 ExprResult Res
= Self
.TransformExpr(IntExpr
);
11771 if (!Res
.isUsable())
11774 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11776 C
.getBeginLoc(), Res
.get());
11777 if (!Res
.isUsable())
11780 ParsedClause
.setIntExprDetails(Res
.get());
11781 NewClause
= OpenACCVectorLengthClause::Create(
11782 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11783 ParsedClause
.getLParenLoc(), ParsedClause
.getIntExprs()[0],
11784 ParsedClause
.getEndLoc());
11787 template <typename Derived
>
11788 void OpenACCClauseTransform
<Derived
>::VisitAsyncClause(
11789 const OpenACCAsyncClause
&C
) {
11790 if (C
.hasIntExpr()) {
11791 ExprResult Res
= Self
.TransformExpr(const_cast<Expr
*>(C
.getIntExpr()));
11792 if (!Res
.isUsable())
11795 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11797 C
.getBeginLoc(), Res
.get());
11798 if (!Res
.isUsable())
11800 ParsedClause
.setIntExprDetails(Res
.get());
11803 NewClause
= OpenACCAsyncClause::Create(
11804 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11805 ParsedClause
.getLParenLoc(),
11806 ParsedClause
.getNumIntExprs() != 0 ? ParsedClause
.getIntExprs()[0]
11808 ParsedClause
.getEndLoc());
11811 template <typename Derived
>
11812 void OpenACCClauseTransform
<Derived
>::VisitWorkerClause(
11813 const OpenACCWorkerClause
&C
) {
11814 if (C
.hasIntExpr()) {
11815 // restrictions on this expression are all "does it exist in certain
11816 // situations" that are not possible to be dependent, so the only check we
11817 // have is that it transforms, and is an int expression.
11818 ExprResult Res
= Self
.TransformExpr(const_cast<Expr
*>(C
.getIntExpr()));
11819 if (!Res
.isUsable())
11822 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11824 C
.getBeginLoc(), Res
.get());
11825 if (!Res
.isUsable())
11827 ParsedClause
.setIntExprDetails(Res
.get());
11830 NewClause
= OpenACCWorkerClause::Create(
11831 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11832 ParsedClause
.getLParenLoc(),
11833 ParsedClause
.getNumIntExprs() != 0 ? ParsedClause
.getIntExprs()[0]
11835 ParsedClause
.getEndLoc());
11838 template <typename Derived
>
11839 void OpenACCClauseTransform
<Derived
>::VisitVectorClause(
11840 const OpenACCVectorClause
&C
) {
11841 if (C
.hasIntExpr()) {
11842 // restrictions on this expression are all "does it exist in certain
11843 // situations" that are not possible to be dependent, so the only check we
11844 // have is that it transforms, and is an int expression.
11845 ExprResult Res
= Self
.TransformExpr(const_cast<Expr
*>(C
.getIntExpr()));
11846 if (!Res
.isUsable())
11849 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11851 C
.getBeginLoc(), Res
.get());
11852 if (!Res
.isUsable())
11854 ParsedClause
.setIntExprDetails(Res
.get());
11857 NewClause
= OpenACCVectorClause::Create(
11858 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11859 ParsedClause
.getLParenLoc(),
11860 ParsedClause
.getNumIntExprs() != 0 ? ParsedClause
.getIntExprs()[0]
11862 ParsedClause
.getEndLoc());
11865 template <typename Derived
>
11866 void OpenACCClauseTransform
<Derived
>::VisitWaitClause(
11867 const OpenACCWaitClause
&C
) {
11868 if (!C
.getLParenLoc().isInvalid()) {
11869 Expr
*DevNumExpr
= nullptr;
11870 llvm::SmallVector
<Expr
*> InstantiatedQueueIdExprs
;
11872 // Instantiate devnum expr if it exists.
11873 if (C
.getDevNumExpr()) {
11874 ExprResult Res
= Self
.TransformExpr(C
.getDevNumExpr());
11875 if (!Res
.isUsable())
11877 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11879 C
.getBeginLoc(), Res
.get());
11880 if (!Res
.isUsable())
11883 DevNumExpr
= Res
.get();
11886 // Instantiate queue ids.
11887 for (Expr
*CurQueueIdExpr
: C
.getQueueIdExprs()) {
11888 ExprResult Res
= Self
.TransformExpr(CurQueueIdExpr
);
11889 if (!Res
.isUsable())
11891 Res
= Self
.getSema().OpenACC().ActOnIntExpr(OpenACCDirectiveKind::Invalid
,
11893 C
.getBeginLoc(), Res
.get());
11894 if (!Res
.isUsable())
11897 InstantiatedQueueIdExprs
.push_back(Res
.get());
11900 ParsedClause
.setWaitDetails(DevNumExpr
, C
.getQueuesLoc(),
11901 std::move(InstantiatedQueueIdExprs
));
11904 NewClause
= OpenACCWaitClause::Create(
11905 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11906 ParsedClause
.getLParenLoc(), ParsedClause
.getDevNumExpr(),
11907 ParsedClause
.getQueuesLoc(), ParsedClause
.getQueueIdExprs(),
11908 ParsedClause
.getEndLoc());
11911 template <typename Derived
>
11912 void OpenACCClauseTransform
<Derived
>::VisitDeviceTypeClause(
11913 const OpenACCDeviceTypeClause
&C
) {
11914 // Nothing to transform here, just create a new version of 'C'.
11915 NewClause
= OpenACCDeviceTypeClause::Create(
11916 Self
.getSema().getASTContext(), C
.getClauseKind(),
11917 ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
11918 C
.getArchitectures(), ParsedClause
.getEndLoc());
11921 template <typename Derived
>
11922 void OpenACCClauseTransform
<Derived
>::VisitAutoClause(
11923 const OpenACCAutoClause
&C
) {
11924 // Nothing to do, so just create a new node.
11925 NewClause
= OpenACCAutoClause::Create(Self
.getSema().getASTContext(),
11926 ParsedClause
.getBeginLoc(),
11927 ParsedClause
.getEndLoc());
11930 template <typename Derived
>
11931 void OpenACCClauseTransform
<Derived
>::VisitIndependentClause(
11932 const OpenACCIndependentClause
&C
) {
11933 NewClause
= OpenACCIndependentClause::Create(Self
.getSema().getASTContext(),
11934 ParsedClause
.getBeginLoc(),
11935 ParsedClause
.getEndLoc());
11938 template <typename Derived
>
11939 void OpenACCClauseTransform
<Derived
>::VisitSeqClause(
11940 const OpenACCSeqClause
&C
) {
11941 NewClause
= OpenACCSeqClause::Create(Self
.getSema().getASTContext(),
11942 ParsedClause
.getBeginLoc(),
11943 ParsedClause
.getEndLoc());
11946 template <typename Derived
>
11947 void OpenACCClauseTransform
<Derived
>::VisitReductionClause(
11948 const OpenACCReductionClause
&C
) {
11949 SmallVector
<Expr
*> TransformedVars
= VisitVarList(C
.getVarList());
11950 SmallVector
<Expr
*> ValidVars
;
11952 for (Expr
*Var
: TransformedVars
) {
11953 ExprResult Res
= Self
.getSema().OpenACC().CheckReductionVar(
11954 ParsedClause
.getDirectiveKind(), C
.getReductionOp(), Var
);
11955 if (Res
.isUsable())
11956 ValidVars
.push_back(Res
.get());
11959 NewClause
= Self
.getSema().OpenACC().CheckReductionClause(
11960 ExistingClauses
, ParsedClause
.getDirectiveKind(),
11961 ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
11962 C
.getReductionOp(), ValidVars
, ParsedClause
.getEndLoc());
11965 template <typename Derived
>
11966 void OpenACCClauseTransform
<Derived
>::VisitCollapseClause(
11967 const OpenACCCollapseClause
&C
) {
11968 Expr
*LoopCount
= const_cast<Expr
*>(C
.getLoopCount());
11969 assert(LoopCount
&& "collapse clause constructed with invalid loop count");
11971 ExprResult NewLoopCount
= Self
.TransformExpr(LoopCount
);
11973 NewLoopCount
= Self
.getSema().OpenACC().ActOnIntExpr(
11974 OpenACCDirectiveKind::Invalid
, ParsedClause
.getClauseKind(),
11975 NewLoopCount
.get()->getBeginLoc(), NewLoopCount
.get());
11978 Self
.getSema().OpenACC().CheckCollapseLoopCount(NewLoopCount
.get());
11980 if (!NewLoopCount
.isUsable())
11983 ParsedClause
.setCollapseDetails(C
.hasForce(), NewLoopCount
.get());
11984 NewClause
= OpenACCCollapseClause::Create(
11985 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
11986 ParsedClause
.getLParenLoc(), ParsedClause
.isForce(),
11987 ParsedClause
.getLoopCount(), ParsedClause
.getEndLoc());
11990 template <typename Derived
>
11991 void OpenACCClauseTransform
<Derived
>::VisitTileClause(
11992 const OpenACCTileClause
&C
) {
11994 llvm::SmallVector
<Expr
*> TransformedExprs
;
11996 for (Expr
*E
: C
.getSizeExprs()) {
11997 ExprResult NewSizeExpr
= Self
.TransformExpr(E
);
11999 if (!NewSizeExpr
.isUsable())
12002 NewSizeExpr
= Self
.getSema().OpenACC().ActOnIntExpr(
12003 OpenACCDirectiveKind::Invalid
, ParsedClause
.getClauseKind(),
12004 NewSizeExpr
.get()->getBeginLoc(), NewSizeExpr
.get());
12006 NewSizeExpr
= Self
.getSema().OpenACC().CheckTileSizeExpr(NewSizeExpr
.get());
12008 if (!NewSizeExpr
.isUsable())
12010 TransformedExprs
.push_back(NewSizeExpr
.get());
12013 ParsedClause
.setIntExprDetails(TransformedExprs
);
12014 NewClause
= OpenACCTileClause::Create(
12015 Self
.getSema().getASTContext(), ParsedClause
.getBeginLoc(),
12016 ParsedClause
.getLParenLoc(), ParsedClause
.getIntExprs(),
12017 ParsedClause
.getEndLoc());
12019 template <typename Derived
>
12020 void OpenACCClauseTransform
<Derived
>::VisitGangClause(
12021 const OpenACCGangClause
&C
) {
12022 llvm::SmallVector
<OpenACCGangKind
> TransformedGangKinds
;
12023 llvm::SmallVector
<Expr
*> TransformedIntExprs
;
12025 for (unsigned I
= 0; I
< C
.getNumExprs(); ++I
) {
12026 ExprResult ER
= Self
.TransformExpr(const_cast<Expr
*>(C
.getExpr(I
).second
));
12027 if (!ER
.isUsable())
12030 ER
= Self
.getSema().OpenACC().CheckGangExpr(C
.getExpr(I
).first
, ER
.get());
12031 if (!ER
.isUsable())
12033 TransformedGangKinds
.push_back(C
.getExpr(I
).first
);
12034 TransformedIntExprs
.push_back(ER
.get());
12037 NewClause
= Self
.getSema().OpenACC().CheckGangClause(
12038 ExistingClauses
, ParsedClause
.getBeginLoc(), ParsedClause
.getLParenLoc(),
12039 TransformedGangKinds
, TransformedIntExprs
, ParsedClause
.getEndLoc());
12042 template <typename Derived
>
12043 OpenACCClause
*TreeTransform
<Derived
>::TransformOpenACCClause(
12044 ArrayRef
<const OpenACCClause
*> ExistingClauses
,
12045 OpenACCDirectiveKind DirKind
, const OpenACCClause
*OldClause
) {
12047 SemaOpenACC::OpenACCParsedClause
ParsedClause(
12048 DirKind
, OldClause
->getClauseKind(), OldClause
->getBeginLoc());
12049 ParsedClause
.setEndLoc(OldClause
->getEndLoc());
12051 if (const auto *WithParms
= dyn_cast
<OpenACCClauseWithParams
>(OldClause
))
12052 ParsedClause
.setLParenLoc(WithParms
->getLParenLoc());
12054 OpenACCClauseTransform
<Derived
> Transform
{*this, ExistingClauses
,
12056 Transform
.Visit(OldClause
);
12058 return Transform
.CreatedClause();
12061 template <typename Derived
>
12062 llvm::SmallVector
<OpenACCClause
*>
12063 TreeTransform
<Derived
>::TransformOpenACCClauseList(
12064 OpenACCDirectiveKind DirKind
, ArrayRef
<const OpenACCClause
*> OldClauses
) {
12065 llvm::SmallVector
<OpenACCClause
*> TransformedClauses
;
12066 for (const auto *Clause
: OldClauses
) {
12067 if (OpenACCClause
*TransformedClause
= getDerived().TransformOpenACCClause(
12068 TransformedClauses
, DirKind
, Clause
))
12069 TransformedClauses
.push_back(TransformedClause
);
12071 return TransformedClauses
;
12074 template <typename Derived
>
12075 StmtResult TreeTransform
<Derived
>::TransformOpenACCComputeConstruct(
12076 OpenACCComputeConstruct
*C
) {
12077 getSema().OpenACC().ActOnConstruct(C
->getDirectiveKind(), C
->getBeginLoc());
12079 llvm::SmallVector
<OpenACCClause
*> TransformedClauses
=
12080 getDerived().TransformOpenACCClauseList(C
->getDirectiveKind(),
12083 if (getSema().OpenACC().ActOnStartStmtDirective(C
->getDirectiveKind(),
12085 return StmtError();
12087 // Transform Structured Block.
12088 SemaOpenACC::AssociatedStmtRAII
AssocStmtRAII(
12089 getSema().OpenACC(), C
->getDirectiveKind(), C
->getDirectiveLoc(),
12090 C
->clauses(), TransformedClauses
);
12091 StmtResult StrBlock
= getDerived().TransformStmt(C
->getStructuredBlock());
12092 StrBlock
= getSema().OpenACC().ActOnAssociatedStmt(
12093 C
->getBeginLoc(), C
->getDirectiveKind(), TransformedClauses
, StrBlock
);
12095 return getDerived().RebuildOpenACCComputeConstruct(
12096 C
->getDirectiveKind(), C
->getBeginLoc(), C
->getDirectiveLoc(),
12097 C
->getEndLoc(), TransformedClauses
, StrBlock
);
12100 template <typename Derived
>
12102 TreeTransform
<Derived
>::TransformOpenACCLoopConstruct(OpenACCLoopConstruct
*C
) {
12104 getSema().OpenACC().ActOnConstruct(C
->getDirectiveKind(), C
->getBeginLoc());
12106 llvm::SmallVector
<OpenACCClause
*> TransformedClauses
=
12107 getDerived().TransformOpenACCClauseList(C
->getDirectiveKind(),
12110 if (getSema().OpenACC().ActOnStartStmtDirective(C
->getDirectiveKind(),
12112 return StmtError();
12115 SemaOpenACC::AssociatedStmtRAII
AssocStmtRAII(
12116 getSema().OpenACC(), C
->getDirectiveKind(), C
->getDirectiveLoc(),
12117 C
->clauses(), TransformedClauses
);
12118 StmtResult Loop
= getDerived().TransformStmt(C
->getLoop());
12119 Loop
= getSema().OpenACC().ActOnAssociatedStmt(
12120 C
->getBeginLoc(), C
->getDirectiveKind(), TransformedClauses
, Loop
);
12122 return getDerived().RebuildOpenACCLoopConstruct(
12123 C
->getBeginLoc(), C
->getDirectiveLoc(), C
->getEndLoc(),
12124 TransformedClauses
, Loop
);
12127 template <typename Derived
>
12128 StmtResult TreeTransform
<Derived
>::TransformOpenACCCombinedConstruct(
12129 OpenACCCombinedConstruct
*C
) {
12130 getSema().OpenACC().ActOnConstruct(C
->getDirectiveKind(), C
->getBeginLoc());
12132 llvm::SmallVector
<OpenACCClause
*> TransformedClauses
=
12133 getDerived().TransformOpenACCClauseList(C
->getDirectiveKind(),
12136 if (getSema().OpenACC().ActOnStartStmtDirective(C
->getDirectiveKind(),
12138 return StmtError();
12141 SemaOpenACC::AssociatedStmtRAII
AssocStmtRAII(
12142 getSema().OpenACC(), C
->getDirectiveKind(), C
->getDirectiveLoc(),
12143 C
->clauses(), TransformedClauses
);
12144 StmtResult Loop
= getDerived().TransformStmt(C
->getLoop());
12145 Loop
= getSema().OpenACC().ActOnAssociatedStmt(
12146 C
->getBeginLoc(), C
->getDirectiveKind(), TransformedClauses
, Loop
);
12148 return getDerived().RebuildOpenACCCombinedConstruct(
12149 C
->getDirectiveKind(), C
->getBeginLoc(), C
->getDirectiveLoc(),
12150 C
->getEndLoc(), TransformedClauses
, Loop
);
12153 template <typename Derived
>
12154 ExprResult TreeTransform
<Derived
>::TransformOpenACCAsteriskSizeExpr(
12155 OpenACCAsteriskSizeExpr
*E
) {
12156 if (getDerived().AlwaysRebuild())
12157 return getDerived().RebuildOpenACCAsteriskSizeExpr(E
->getLocation());
12158 // Nothing can ever change, so there is never anything to transform.
12162 //===----------------------------------------------------------------------===//
12163 // Expression transformation
12164 //===----------------------------------------------------------------------===//
12165 template<typename Derived
>
12167 TreeTransform
<Derived
>::TransformConstantExpr(ConstantExpr
*E
) {
12168 return TransformExpr(E
->getSubExpr());
12171 template <typename Derived
>
12172 ExprResult TreeTransform
<Derived
>::TransformSYCLUniqueStableNameExpr(
12173 SYCLUniqueStableNameExpr
*E
) {
12174 if (!E
->isTypeDependent())
12177 TypeSourceInfo
*NewT
= getDerived().TransformType(E
->getTypeSourceInfo());
12180 return ExprError();
12182 if (!getDerived().AlwaysRebuild() && E
->getTypeSourceInfo() == NewT
)
12185 return getDerived().RebuildSYCLUniqueStableNameExpr(
12186 E
->getLocation(), E
->getLParenLocation(), E
->getRParenLocation(), NewT
);
12189 template<typename Derived
>
12191 TreeTransform
<Derived
>::TransformPredefinedExpr(PredefinedExpr
*E
) {
12192 if (!E
->isTypeDependent())
12195 return getDerived().RebuildPredefinedExpr(E
->getLocation(),
12196 E
->getIdentKind());
12199 template<typename Derived
>
12201 TreeTransform
<Derived
>::TransformDeclRefExpr(DeclRefExpr
*E
) {
12202 NestedNameSpecifierLoc QualifierLoc
;
12203 if (E
->getQualifierLoc()) {
12205 = getDerived().TransformNestedNameSpecifierLoc(E
->getQualifierLoc());
12207 return ExprError();
12211 = cast_or_null
<ValueDecl
>(getDerived().TransformDecl(E
->getLocation(),
12214 return ExprError();
12216 NamedDecl
*Found
= ND
;
12217 if (E
->getFoundDecl() != E
->getDecl()) {
12218 Found
= cast_or_null
<NamedDecl
>(
12219 getDerived().TransformDecl(E
->getLocation(), E
->getFoundDecl()));
12221 return ExprError();
12224 DeclarationNameInfo NameInfo
= E
->getNameInfo();
12225 if (NameInfo
.getName()) {
12226 NameInfo
= getDerived().TransformDeclarationNameInfo(NameInfo
);
12227 if (!NameInfo
.getName())
12228 return ExprError();
12231 if (!getDerived().AlwaysRebuild() &&
12232 !E
->isCapturedByCopyInLambdaWithExplicitObjectParameter() &&
12233 QualifierLoc
== E
->getQualifierLoc() && ND
== E
->getDecl() &&
12234 Found
== E
->getFoundDecl() &&
12235 NameInfo
.getName() == E
->getDecl()->getDeclName() &&
12236 !E
->hasExplicitTemplateArgs()) {
12238 // Mark it referenced in the new context regardless.
12239 // FIXME: this is a bit instantiation-specific.
12240 SemaRef
.MarkDeclRefReferenced(E
);
12245 TemplateArgumentListInfo TransArgs
, *TemplateArgs
= nullptr;
12246 if (E
->hasExplicitTemplateArgs()) {
12247 TemplateArgs
= &TransArgs
;
12248 TransArgs
.setLAngleLoc(E
->getLAngleLoc());
12249 TransArgs
.setRAngleLoc(E
->getRAngleLoc());
12250 if (getDerived().TransformTemplateArguments(E
->getTemplateArgs(),
12251 E
->getNumTemplateArgs(),
12253 return ExprError();
12256 return getDerived().RebuildDeclRefExpr(QualifierLoc
, ND
, NameInfo
,
12257 Found
, TemplateArgs
);
12260 template<typename Derived
>
12262 TreeTransform
<Derived
>::TransformIntegerLiteral(IntegerLiteral
*E
) {
12266 template <typename Derived
>
12267 ExprResult TreeTransform
<Derived
>::TransformFixedPointLiteral(
12268 FixedPointLiteral
*E
) {
12272 template<typename Derived
>
12274 TreeTransform
<Derived
>::TransformFloatingLiteral(FloatingLiteral
*E
) {
12278 template<typename Derived
>
12280 TreeTransform
<Derived
>::TransformImaginaryLiteral(ImaginaryLiteral
*E
) {
12284 template<typename Derived
>
12286 TreeTransform
<Derived
>::TransformStringLiteral(StringLiteral
*E
) {
12290 template<typename Derived
>
12292 TreeTransform
<Derived
>::TransformCharacterLiteral(CharacterLiteral
*E
) {
12296 template<typename Derived
>
12298 TreeTransform
<Derived
>::TransformUserDefinedLiteral(UserDefinedLiteral
*E
) {
12299 return getDerived().TransformCallExpr(E
);
12302 template<typename Derived
>
12304 TreeTransform
<Derived
>::TransformGenericSelectionExpr(GenericSelectionExpr
*E
) {
12305 ExprResult ControllingExpr
;
12306 TypeSourceInfo
*ControllingType
= nullptr;
12307 if (E
->isExprPredicate())
12308 ControllingExpr
= getDerived().TransformExpr(E
->getControllingExpr());
12310 ControllingType
= getDerived().TransformType(E
->getControllingType());
12312 if (ControllingExpr
.isInvalid() && !ControllingType
)
12313 return ExprError();
12315 SmallVector
<Expr
*, 4> AssocExprs
;
12316 SmallVector
<TypeSourceInfo
*, 4> AssocTypes
;
12317 for (const GenericSelectionExpr::Association Assoc
: E
->associations()) {
12318 TypeSourceInfo
*TSI
= Assoc
.getTypeSourceInfo();
12320 TypeSourceInfo
*AssocType
= getDerived().TransformType(TSI
);
12322 return ExprError();
12323 AssocTypes
.push_back(AssocType
);
12325 AssocTypes
.push_back(nullptr);
12328 ExprResult AssocExpr
=
12329 getDerived().TransformExpr(Assoc
.getAssociationExpr());
12330 if (AssocExpr
.isInvalid())
12331 return ExprError();
12332 AssocExprs
.push_back(AssocExpr
.get());
12335 if (!ControllingType
)
12336 return getDerived().RebuildGenericSelectionExpr(E
->getGenericLoc(),
12337 E
->getDefaultLoc(),
12339 ControllingExpr
.get(),
12342 return getDerived().RebuildGenericSelectionExpr(
12343 E
->getGenericLoc(), E
->getDefaultLoc(), E
->getRParenLoc(),
12344 ControllingType
, AssocTypes
, AssocExprs
);
12347 template<typename Derived
>
12349 TreeTransform
<Derived
>::TransformParenExpr(ParenExpr
*E
) {
12350 ExprResult SubExpr
= getDerived().TransformExpr(E
->getSubExpr());
12351 if (SubExpr
.isInvalid())
12352 return ExprError();
12354 if (!getDerived().AlwaysRebuild() && SubExpr
.get() == E
->getSubExpr())
12357 return getDerived().RebuildParenExpr(SubExpr
.get(), E
->getLParen(),
12361 /// The operand of a unary address-of operator has special rules: it's
12362 /// allowed to refer to a non-static member of a class even if there's no 'this'
12363 /// object available.
12364 template<typename Derived
>
12366 TreeTransform
<Derived
>::TransformAddressOfOperand(Expr
*E
) {
12367 if (DependentScopeDeclRefExpr
*DRE
= dyn_cast
<DependentScopeDeclRefExpr
>(E
))
12368 return getDerived().TransformDependentScopeDeclRefExpr(
12369 DRE
, /*IsAddressOfOperand=*/true, nullptr);
12370 else if (UnresolvedLookupExpr
*ULE
= dyn_cast
<UnresolvedLookupExpr
>(E
))
12371 return getDerived().TransformUnresolvedLookupExpr(
12372 ULE
, /*IsAddressOfOperand=*/true);
12374 return getDerived().TransformExpr(E
);
12377 template<typename Derived
>
12379 TreeTransform
<Derived
>::TransformUnaryOperator(UnaryOperator
*E
) {
12380 ExprResult SubExpr
;
12381 if (E
->getOpcode() == UO_AddrOf
)
12382 SubExpr
= TransformAddressOfOperand(E
->getSubExpr());
12384 SubExpr
= TransformExpr(E
->getSubExpr());
12385 if (SubExpr
.isInvalid())
12386 return ExprError();
12388 if (!getDerived().AlwaysRebuild() && SubExpr
.get() == E
->getSubExpr())
12391 return getDerived().RebuildUnaryOperator(E
->getOperatorLoc(),
12396 template<typename Derived
>
12398 TreeTransform
<Derived
>::TransformOffsetOfExpr(OffsetOfExpr
*E
) {
12399 // Transform the type.
12400 TypeSourceInfo
*Type
= getDerived().TransformType(E
->getTypeSourceInfo());
12402 return ExprError();
12404 // Transform all of the components into components similar to what the
12406 // FIXME: It would be slightly more efficient in the non-dependent case to
12407 // just map FieldDecls, rather than requiring the rebuilder to look for
12408 // the fields again. However, __builtin_offsetof is rare enough in
12409 // template code that we don't care.
12410 bool ExprChanged
= false;
12411 typedef Sema::OffsetOfComponent Component
;
12412 SmallVector
<Component
, 4> Components
;
12413 for (unsigned I
= 0, N
= E
->getNumComponents(); I
!= N
; ++I
) {
12414 const OffsetOfNode
&ON
= E
->getComponent(I
);
12416 Comp
.isBrackets
= true;
12417 Comp
.LocStart
= ON
.getSourceRange().getBegin();
12418 Comp
.LocEnd
= ON
.getSourceRange().getEnd();
12419 switch (ON
.getKind()) {
12420 case OffsetOfNode::Array
: {
12421 Expr
*FromIndex
= E
->getIndexExpr(ON
.getArrayExprIndex());
12422 ExprResult Index
= getDerived().TransformExpr(FromIndex
);
12423 if (Index
.isInvalid())
12424 return ExprError();
12426 ExprChanged
= ExprChanged
|| Index
.get() != FromIndex
;
12427 Comp
.isBrackets
= true;
12428 Comp
.U
.E
= Index
.get();
12432 case OffsetOfNode::Field
:
12433 case OffsetOfNode::Identifier
:
12434 Comp
.isBrackets
= false;
12435 Comp
.U
.IdentInfo
= ON
.getFieldName();
12436 if (!Comp
.U
.IdentInfo
)
12441 case OffsetOfNode::Base
:
12442 // Will be recomputed during the rebuild.
12446 Components
.push_back(Comp
);
12449 // If nothing changed, retain the existing expression.
12450 if (!getDerived().AlwaysRebuild() &&
12451 Type
== E
->getTypeSourceInfo() &&
12455 // Build a new offsetof expression.
12456 return getDerived().RebuildOffsetOfExpr(E
->getOperatorLoc(), Type
,
12457 Components
, E
->getRParenLoc());
12460 template<typename Derived
>
12462 TreeTransform
<Derived
>::TransformOpaqueValueExpr(OpaqueValueExpr
*E
) {
12463 assert((!E
->getSourceExpr() || getDerived().AlreadyTransformed(E
->getType())) &&
12464 "opaque value expression requires transformation");
12468 template<typename Derived
>
12470 TreeTransform
<Derived
>::TransformTypoExpr(TypoExpr
*E
) {
12474 template <typename Derived
>
12475 ExprResult TreeTransform
<Derived
>::TransformRecoveryExpr(RecoveryExpr
*E
) {
12476 llvm::SmallVector
<Expr
*, 8> Children
;
12477 bool Changed
= false;
12478 for (Expr
*C
: E
->subExpressions()) {
12479 ExprResult NewC
= getDerived().TransformExpr(C
);
12480 if (NewC
.isInvalid())
12481 return ExprError();
12482 Children
.push_back(NewC
.get());
12484 Changed
|= NewC
.get() != C
;
12486 if (!getDerived().AlwaysRebuild() && !Changed
)
12488 return getDerived().RebuildRecoveryExpr(E
->getBeginLoc(), E
->getEndLoc(),
12489 Children
, E
->getType());
12492 template<typename Derived
>
12494 TreeTransform
<Derived
>::TransformPseudoObjectExpr(PseudoObjectExpr
*E
) {
12495 // Rebuild the syntactic form. The original syntactic form has
12496 // opaque-value expressions in it, so strip those away and rebuild
12497 // the result. This is a really awful way of doing this, but the
12498 // better solution (rebuilding the semantic expressions and
12499 // rebinding OVEs as necessary) doesn't work; we'd need
12500 // TreeTransform to not strip away implicit conversions.
12501 Expr
*newSyntacticForm
= SemaRef
.PseudoObject().recreateSyntacticForm(E
);
12502 ExprResult result
= getDerived().TransformExpr(newSyntacticForm
);
12503 if (result
.isInvalid()) return ExprError();
12505 // If that gives us a pseudo-object result back, the pseudo-object
12506 // expression must have been an lvalue-to-rvalue conversion which we
12508 if (result
.get()->hasPlaceholderType(BuiltinType::PseudoObject
))
12509 result
= SemaRef
.PseudoObject().checkRValue(result
.get());
12514 template<typename Derived
>
12516 TreeTransform
<Derived
>::TransformUnaryExprOrTypeTraitExpr(
12517 UnaryExprOrTypeTraitExpr
*E
) {
12518 if (E
->isArgumentType()) {
12519 TypeSourceInfo
*OldT
= E
->getArgumentTypeInfo();
12521 TypeSourceInfo
*NewT
= getDerived().TransformType(OldT
);
12523 return ExprError();
12525 if (!getDerived().AlwaysRebuild() && OldT
== NewT
)
12528 return getDerived().RebuildUnaryExprOrTypeTrait(NewT
, E
->getOperatorLoc(),
12530 E
->getSourceRange());
12533 // C++0x [expr.sizeof]p1:
12534 // The operand is either an expression, which is an unevaluated operand
12536 EnterExpressionEvaluationContext
Unevaluated(
12537 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
,
12538 Sema::ReuseLambdaContextDecl
);
12540 // Try to recover if we have something like sizeof(T::X) where X is a type.
12541 // Notably, there must be *exactly* one set of parens if X is a type.
12542 TypeSourceInfo
*RecoveryTSI
= nullptr;
12543 ExprResult SubExpr
;
12544 auto *PE
= dyn_cast
<ParenExpr
>(E
->getArgumentExpr());
12546 PE
? dyn_cast
<DependentScopeDeclRefExpr
>(PE
->getSubExpr()) : nullptr)
12547 SubExpr
= getDerived().TransformParenDependentScopeDeclRefExpr(
12548 PE
, DRE
, false, &RecoveryTSI
);
12550 SubExpr
= getDerived().TransformExpr(E
->getArgumentExpr());
12553 return getDerived().RebuildUnaryExprOrTypeTrait(
12554 RecoveryTSI
, E
->getOperatorLoc(), E
->getKind(), E
->getSourceRange());
12555 } else if (SubExpr
.isInvalid())
12556 return ExprError();
12558 if (!getDerived().AlwaysRebuild() && SubExpr
.get() == E
->getArgumentExpr())
12561 return getDerived().RebuildUnaryExprOrTypeTrait(SubExpr
.get(),
12562 E
->getOperatorLoc(),
12564 E
->getSourceRange());
12567 template<typename Derived
>
12569 TreeTransform
<Derived
>::TransformArraySubscriptExpr(ArraySubscriptExpr
*E
) {
12570 ExprResult LHS
= getDerived().TransformExpr(E
->getLHS());
12571 if (LHS
.isInvalid())
12572 return ExprError();
12574 ExprResult RHS
= getDerived().TransformExpr(E
->getRHS());
12575 if (RHS
.isInvalid())
12576 return ExprError();
12579 if (!getDerived().AlwaysRebuild() &&
12580 LHS
.get() == E
->getLHS() &&
12581 RHS
.get() == E
->getRHS())
12584 return getDerived().RebuildArraySubscriptExpr(
12586 /*FIXME:*/ E
->getLHS()->getBeginLoc(), RHS
.get(), E
->getRBracketLoc());
12589 template <typename Derived
>
12591 TreeTransform
<Derived
>::TransformMatrixSubscriptExpr(MatrixSubscriptExpr
*E
) {
12592 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
12593 if (Base
.isInvalid())
12594 return ExprError();
12596 ExprResult RowIdx
= getDerived().TransformExpr(E
->getRowIdx());
12597 if (RowIdx
.isInvalid())
12598 return ExprError();
12600 ExprResult ColumnIdx
= getDerived().TransformExpr(E
->getColumnIdx());
12601 if (ColumnIdx
.isInvalid())
12602 return ExprError();
12604 if (!getDerived().AlwaysRebuild() && Base
.get() == E
->getBase() &&
12605 RowIdx
.get() == E
->getRowIdx() && ColumnIdx
.get() == E
->getColumnIdx())
12608 return getDerived().RebuildMatrixSubscriptExpr(
12609 Base
.get(), RowIdx
.get(), ColumnIdx
.get(), E
->getRBracketLoc());
12612 template <typename Derived
>
12614 TreeTransform
<Derived
>::TransformArraySectionExpr(ArraySectionExpr
*E
) {
12615 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
12616 if (Base
.isInvalid())
12617 return ExprError();
12619 ExprResult LowerBound
;
12620 if (E
->getLowerBound()) {
12621 LowerBound
= getDerived().TransformExpr(E
->getLowerBound());
12622 if (LowerBound
.isInvalid())
12623 return ExprError();
12627 if (E
->getLength()) {
12628 Length
= getDerived().TransformExpr(E
->getLength());
12629 if (Length
.isInvalid())
12630 return ExprError();
12634 if (E
->isOMPArraySection()) {
12635 if (Expr
*Str
= E
->getStride()) {
12636 Stride
= getDerived().TransformExpr(Str
);
12637 if (Stride
.isInvalid())
12638 return ExprError();
12642 if (!getDerived().AlwaysRebuild() && Base
.get() == E
->getBase() &&
12643 LowerBound
.get() == E
->getLowerBound() &&
12644 Length
.get() == E
->getLength() &&
12645 (E
->isOpenACCArraySection() || Stride
.get() == E
->getStride()))
12648 return getDerived().RebuildArraySectionExpr(
12649 E
->isOMPArraySection(), Base
.get(), E
->getBase()->getEndLoc(),
12650 LowerBound
.get(), E
->getColonLocFirst(),
12651 E
->isOMPArraySection() ? E
->getColonLocSecond() : SourceLocation
{},
12652 Length
.get(), Stride
.get(), E
->getRBracketLoc());
12655 template <typename Derived
>
12657 TreeTransform
<Derived
>::TransformOMPArrayShapingExpr(OMPArrayShapingExpr
*E
) {
12658 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
12659 if (Base
.isInvalid())
12660 return ExprError();
12662 SmallVector
<Expr
*, 4> Dims
;
12663 bool ErrorFound
= false;
12664 for (Expr
*Dim
: E
->getDimensions()) {
12665 ExprResult DimRes
= getDerived().TransformExpr(Dim
);
12666 if (DimRes
.isInvalid()) {
12670 Dims
.push_back(DimRes
.get());
12674 return ExprError();
12675 return getDerived().RebuildOMPArrayShapingExpr(Base
.get(), E
->getLParenLoc(),
12676 E
->getRParenLoc(), Dims
,
12677 E
->getBracketsRanges());
12680 template <typename Derived
>
12682 TreeTransform
<Derived
>::TransformOMPIteratorExpr(OMPIteratorExpr
*E
) {
12683 unsigned NumIterators
= E
->numOfIterators();
12684 SmallVector
<SemaOpenMP::OMPIteratorData
, 4> Data(NumIterators
);
12686 bool ErrorFound
= false;
12687 bool NeedToRebuild
= getDerived().AlwaysRebuild();
12688 for (unsigned I
= 0; I
< NumIterators
; ++I
) {
12689 auto *D
= cast
<VarDecl
>(E
->getIteratorDecl(I
));
12690 Data
[I
].DeclIdent
= D
->getIdentifier();
12691 Data
[I
].DeclIdentLoc
= D
->getLocation();
12692 if (D
->getLocation() == D
->getBeginLoc()) {
12693 assert(SemaRef
.Context
.hasSameType(D
->getType(), SemaRef
.Context
.IntTy
) &&
12694 "Implicit type must be int.");
12696 TypeSourceInfo
*TSI
= getDerived().TransformType(D
->getTypeSourceInfo());
12697 QualType DeclTy
= getDerived().TransformType(D
->getType());
12698 Data
[I
].Type
= SemaRef
.CreateParsedType(DeclTy
, TSI
);
12700 OMPIteratorExpr::IteratorRange Range
= E
->getIteratorRange(I
);
12701 ExprResult Begin
= getDerived().TransformExpr(Range
.Begin
);
12702 ExprResult End
= getDerived().TransformExpr(Range
.End
);
12703 ExprResult Step
= getDerived().TransformExpr(Range
.Step
);
12704 ErrorFound
= ErrorFound
||
12705 !(!D
->getTypeSourceInfo() || (Data
[I
].Type
.getAsOpaquePtr() &&
12706 !Data
[I
].Type
.get().isNull())) ||
12707 Begin
.isInvalid() || End
.isInvalid() || Step
.isInvalid();
12710 Data
[I
].Range
.Begin
= Begin
.get();
12711 Data
[I
].Range
.End
= End
.get();
12712 Data
[I
].Range
.Step
= Step
.get();
12713 Data
[I
].AssignLoc
= E
->getAssignLoc(I
);
12714 Data
[I
].ColonLoc
= E
->getColonLoc(I
);
12715 Data
[I
].SecColonLoc
= E
->getSecondColonLoc(I
);
12718 (D
->getTypeSourceInfo() && Data
[I
].Type
.get().getTypePtrOrNull() !=
12719 D
->getType().getTypePtrOrNull()) ||
12720 Range
.Begin
!= Data
[I
].Range
.Begin
|| Range
.End
!= Data
[I
].Range
.End
||
12721 Range
.Step
!= Data
[I
].Range
.Step
;
12724 return ExprError();
12725 if (!NeedToRebuild
)
12728 ExprResult Res
= getDerived().RebuildOMPIteratorExpr(
12729 E
->getIteratorKwLoc(), E
->getLParenLoc(), E
->getRParenLoc(), Data
);
12730 if (!Res
.isUsable())
12732 auto *IE
= cast
<OMPIteratorExpr
>(Res
.get());
12733 for (unsigned I
= 0; I
< NumIterators
; ++I
)
12734 getDerived().transformedLocalDecl(E
->getIteratorDecl(I
),
12735 IE
->getIteratorDecl(I
));
12739 template<typename Derived
>
12741 TreeTransform
<Derived
>::TransformCallExpr(CallExpr
*E
) {
12742 // Transform the callee.
12743 ExprResult Callee
= getDerived().TransformExpr(E
->getCallee());
12744 if (Callee
.isInvalid())
12745 return ExprError();
12747 // Transform arguments.
12748 bool ArgChanged
= false;
12749 SmallVector
<Expr
*, 8> Args
;
12750 if (getDerived().TransformExprs(E
->getArgs(), E
->getNumArgs(), true, Args
,
12752 return ExprError();
12754 if (!getDerived().AlwaysRebuild() &&
12755 Callee
.get() == E
->getCallee() &&
12757 return SemaRef
.MaybeBindToTemporary(E
);
12759 // FIXME: Wrong source location information for the '('.
12760 SourceLocation FakeLParenLoc
12761 = ((Expr
*)Callee
.get())->getSourceRange().getBegin();
12763 Sema::FPFeaturesStateRAII
FPFeaturesState(getSema());
12764 if (E
->hasStoredFPFeatures()) {
12765 FPOptionsOverride NewOverrides
= E
->getFPFeatures();
12766 getSema().CurFPFeatures
=
12767 NewOverrides
.applyOverrides(getSema().getLangOpts());
12768 getSema().FpPragmaStack
.CurrentValue
= NewOverrides
;
12771 return getDerived().RebuildCallExpr(Callee
.get(), FakeLParenLoc
,
12773 E
->getRParenLoc());
12776 template<typename Derived
>
12778 TreeTransform
<Derived
>::TransformMemberExpr(MemberExpr
*E
) {
12779 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
12780 if (Base
.isInvalid())
12781 return ExprError();
12783 NestedNameSpecifierLoc QualifierLoc
;
12784 if (E
->hasQualifier()) {
12786 = getDerived().TransformNestedNameSpecifierLoc(E
->getQualifierLoc());
12789 return ExprError();
12791 SourceLocation TemplateKWLoc
= E
->getTemplateKeywordLoc();
12794 = cast_or_null
<ValueDecl
>(getDerived().TransformDecl(E
->getMemberLoc(),
12795 E
->getMemberDecl()));
12797 return ExprError();
12799 NamedDecl
*FoundDecl
= E
->getFoundDecl();
12800 if (FoundDecl
== E
->getMemberDecl()) {
12801 FoundDecl
= Member
;
12803 FoundDecl
= cast_or_null
<NamedDecl
>(
12804 getDerived().TransformDecl(E
->getMemberLoc(), FoundDecl
));
12806 return ExprError();
12809 if (!getDerived().AlwaysRebuild() &&
12810 Base
.get() == E
->getBase() &&
12811 QualifierLoc
== E
->getQualifierLoc() &&
12812 Member
== E
->getMemberDecl() &&
12813 FoundDecl
== E
->getFoundDecl() &&
12814 !E
->hasExplicitTemplateArgs()) {
12816 // Skip for member expression of (this->f), rebuilt thisi->f is needed
12817 // for Openmp where the field need to be privatizized in the case.
12818 if (!(isa
<CXXThisExpr
>(E
->getBase()) &&
12819 getSema().OpenMP().isOpenMPRebuildMemberExpr(
12820 cast
<ValueDecl
>(Member
)))) {
12821 // Mark it referenced in the new context regardless.
12822 // FIXME: this is a bit instantiation-specific.
12823 SemaRef
.MarkMemberReferenced(E
);
12828 TemplateArgumentListInfo TransArgs
;
12829 if (E
->hasExplicitTemplateArgs()) {
12830 TransArgs
.setLAngleLoc(E
->getLAngleLoc());
12831 TransArgs
.setRAngleLoc(E
->getRAngleLoc());
12832 if (getDerived().TransformTemplateArguments(E
->getTemplateArgs(),
12833 E
->getNumTemplateArgs(),
12835 return ExprError();
12838 // FIXME: Bogus source location for the operator
12839 SourceLocation FakeOperatorLoc
=
12840 SemaRef
.getLocForEndOfToken(E
->getBase()->getSourceRange().getEnd());
12842 // FIXME: to do this check properly, we will need to preserve the
12843 // first-qualifier-in-scope here, just in case we had a dependent
12844 // base (and therefore couldn't do the check) and a
12845 // nested-name-qualifier (and therefore could do the lookup).
12846 NamedDecl
*FirstQualifierInScope
= nullptr;
12847 DeclarationNameInfo MemberNameInfo
= E
->getMemberNameInfo();
12848 if (MemberNameInfo
.getName()) {
12849 MemberNameInfo
= getDerived().TransformDeclarationNameInfo(MemberNameInfo
);
12850 if (!MemberNameInfo
.getName())
12851 return ExprError();
12854 return getDerived().RebuildMemberExpr(Base
.get(), FakeOperatorLoc
,
12861 (E
->hasExplicitTemplateArgs()
12862 ? &TransArgs
: nullptr),
12863 FirstQualifierInScope
);
12866 template<typename Derived
>
12868 TreeTransform
<Derived
>::TransformBinaryOperator(BinaryOperator
*E
) {
12869 ExprResult LHS
= getDerived().TransformExpr(E
->getLHS());
12870 if (LHS
.isInvalid())
12871 return ExprError();
12874 getDerived().TransformInitializer(E
->getRHS(), /*NotCopyInit=*/false);
12875 if (RHS
.isInvalid())
12876 return ExprError();
12878 if (!getDerived().AlwaysRebuild() &&
12879 LHS
.get() == E
->getLHS() &&
12880 RHS
.get() == E
->getRHS())
12883 if (E
->isCompoundAssignmentOp())
12884 // FPFeatures has already been established from trailing storage
12885 return getDerived().RebuildBinaryOperator(
12886 E
->getOperatorLoc(), E
->getOpcode(), LHS
.get(), RHS
.get());
12887 Sema::FPFeaturesStateRAII
FPFeaturesState(getSema());
12888 FPOptionsOverride
NewOverrides(E
->getFPFeatures());
12889 getSema().CurFPFeatures
=
12890 NewOverrides
.applyOverrides(getSema().getLangOpts());
12891 getSema().FpPragmaStack
.CurrentValue
= NewOverrides
;
12892 return getDerived().RebuildBinaryOperator(E
->getOperatorLoc(), E
->getOpcode(),
12893 LHS
.get(), RHS
.get());
12896 template <typename Derived
>
12897 ExprResult TreeTransform
<Derived
>::TransformCXXRewrittenBinaryOperator(
12898 CXXRewrittenBinaryOperator
*E
) {
12899 CXXRewrittenBinaryOperator::DecomposedForm Decomp
= E
->getDecomposedForm();
12901 ExprResult LHS
= getDerived().TransformExpr(const_cast<Expr
*>(Decomp
.LHS
));
12902 if (LHS
.isInvalid())
12903 return ExprError();
12905 ExprResult RHS
= getDerived().TransformExpr(const_cast<Expr
*>(Decomp
.RHS
));
12906 if (RHS
.isInvalid())
12907 return ExprError();
12909 // Extract the already-resolved callee declarations so that we can restrict
12910 // ourselves to using them as the unqualified lookup results when rebuilding.
12911 UnresolvedSet
<2> UnqualLookups
;
12912 bool ChangedAnyLookups
= false;
12913 Expr
*PossibleBinOps
[] = {E
->getSemanticForm(),
12914 const_cast<Expr
*>(Decomp
.InnerBinOp
)};
12915 for (Expr
*PossibleBinOp
: PossibleBinOps
) {
12916 auto *Op
= dyn_cast
<CXXOperatorCallExpr
>(PossibleBinOp
->IgnoreImplicit());
12919 auto *Callee
= dyn_cast
<DeclRefExpr
>(Op
->getCallee()->IgnoreImplicit());
12920 if (!Callee
|| isa
<CXXMethodDecl
>(Callee
->getDecl()))
12923 // Transform the callee in case we built a call to a local extern
12925 NamedDecl
*Found
= cast_or_null
<NamedDecl
>(getDerived().TransformDecl(
12926 E
->getOperatorLoc(), Callee
->getFoundDecl()));
12928 return ExprError();
12929 if (Found
!= Callee
->getFoundDecl())
12930 ChangedAnyLookups
= true;
12931 UnqualLookups
.addDecl(Found
);
12934 if (!getDerived().AlwaysRebuild() && !ChangedAnyLookups
&&
12935 LHS
.get() == Decomp
.LHS
&& RHS
.get() == Decomp
.RHS
) {
12936 // Mark all functions used in the rewrite as referenced. Note that when
12937 // a < b is rewritten to (a <=> b) < 0, both the <=> and the < might be
12938 // function calls, and/or there might be a user-defined conversion sequence
12939 // applied to the operands of the <.
12940 // FIXME: this is a bit instantiation-specific.
12941 const Expr
*StopAt
[] = {Decomp
.LHS
, Decomp
.RHS
};
12942 SemaRef
.MarkDeclarationsReferencedInExpr(E
, false, StopAt
);
12946 return getDerived().RebuildCXXRewrittenBinaryOperator(
12947 E
->getOperatorLoc(), Decomp
.Opcode
, UnqualLookups
, LHS
.get(), RHS
.get());
12950 template<typename Derived
>
12952 TreeTransform
<Derived
>::TransformCompoundAssignOperator(
12953 CompoundAssignOperator
*E
) {
12954 Sema::FPFeaturesStateRAII
FPFeaturesState(getSema());
12955 FPOptionsOverride
NewOverrides(E
->getFPFeatures());
12956 getSema().CurFPFeatures
=
12957 NewOverrides
.applyOverrides(getSema().getLangOpts());
12958 getSema().FpPragmaStack
.CurrentValue
= NewOverrides
;
12959 return getDerived().TransformBinaryOperator(E
);
12962 template<typename Derived
>
12963 ExprResult TreeTransform
<Derived
>::
12964 TransformBinaryConditionalOperator(BinaryConditionalOperator
*e
) {
12965 // Just rebuild the common and RHS expressions and see whether we
12966 // get any changes.
12968 ExprResult commonExpr
= getDerived().TransformExpr(e
->getCommon());
12969 if (commonExpr
.isInvalid())
12970 return ExprError();
12972 ExprResult rhs
= getDerived().TransformExpr(e
->getFalseExpr());
12973 if (rhs
.isInvalid())
12974 return ExprError();
12976 if (!getDerived().AlwaysRebuild() &&
12977 commonExpr
.get() == e
->getCommon() &&
12978 rhs
.get() == e
->getFalseExpr())
12981 return getDerived().RebuildConditionalOperator(commonExpr
.get(),
12982 e
->getQuestionLoc(),
12988 template<typename Derived
>
12990 TreeTransform
<Derived
>::TransformConditionalOperator(ConditionalOperator
*E
) {
12991 ExprResult Cond
= getDerived().TransformExpr(E
->getCond());
12992 if (Cond
.isInvalid())
12993 return ExprError();
12995 ExprResult LHS
= getDerived().TransformExpr(E
->getLHS());
12996 if (LHS
.isInvalid())
12997 return ExprError();
12999 ExprResult RHS
= getDerived().TransformExpr(E
->getRHS());
13000 if (RHS
.isInvalid())
13001 return ExprError();
13003 if (!getDerived().AlwaysRebuild() &&
13004 Cond
.get() == E
->getCond() &&
13005 LHS
.get() == E
->getLHS() &&
13006 RHS
.get() == E
->getRHS())
13009 return getDerived().RebuildConditionalOperator(Cond
.get(),
13010 E
->getQuestionLoc(),
13016 template<typename Derived
>
13018 TreeTransform
<Derived
>::TransformImplicitCastExpr(ImplicitCastExpr
*E
) {
13019 // Implicit casts are eliminated during transformation, since they
13020 // will be recomputed by semantic analysis after transformation.
13021 return getDerived().TransformExpr(E
->getSubExprAsWritten());
13024 template<typename Derived
>
13026 TreeTransform
<Derived
>::TransformCStyleCastExpr(CStyleCastExpr
*E
) {
13027 TypeSourceInfo
*Type
= getDerived().TransformType(E
->getTypeInfoAsWritten());
13029 return ExprError();
13032 = getDerived().TransformExpr(E
->getSubExprAsWritten());
13033 if (SubExpr
.isInvalid())
13034 return ExprError();
13036 if (!getDerived().AlwaysRebuild() &&
13037 Type
== E
->getTypeInfoAsWritten() &&
13038 SubExpr
.get() == E
->getSubExpr())
13041 return getDerived().RebuildCStyleCastExpr(E
->getLParenLoc(),
13047 template<typename Derived
>
13049 TreeTransform
<Derived
>::TransformCompoundLiteralExpr(CompoundLiteralExpr
*E
) {
13050 TypeSourceInfo
*OldT
= E
->getTypeSourceInfo();
13051 TypeSourceInfo
*NewT
= getDerived().TransformType(OldT
);
13053 return ExprError();
13055 ExprResult Init
= getDerived().TransformExpr(E
->getInitializer());
13056 if (Init
.isInvalid())
13057 return ExprError();
13059 if (!getDerived().AlwaysRebuild() &&
13061 Init
.get() == E
->getInitializer())
13062 return SemaRef
.MaybeBindToTemporary(E
);
13064 // Note: the expression type doesn't necessarily match the
13065 // type-as-written, but that's okay, because it should always be
13066 // derivable from the initializer.
13068 return getDerived().RebuildCompoundLiteralExpr(
13069 E
->getLParenLoc(), NewT
,
13070 /*FIXME:*/ E
->getInitializer()->getEndLoc(), Init
.get());
13073 template<typename Derived
>
13075 TreeTransform
<Derived
>::TransformExtVectorElementExpr(ExtVectorElementExpr
*E
) {
13076 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
13077 if (Base
.isInvalid())
13078 return ExprError();
13080 if (!getDerived().AlwaysRebuild() &&
13081 Base
.get() == E
->getBase())
13084 // FIXME: Bad source location
13085 SourceLocation FakeOperatorLoc
=
13086 SemaRef
.getLocForEndOfToken(E
->getBase()->getEndLoc());
13087 return getDerived().RebuildExtVectorElementExpr(
13088 Base
.get(), FakeOperatorLoc
, E
->isArrow(), E
->getAccessorLoc(),
13092 template<typename Derived
>
13094 TreeTransform
<Derived
>::TransformInitListExpr(InitListExpr
*E
) {
13095 if (InitListExpr
*Syntactic
= E
->getSyntacticForm())
13098 bool InitChanged
= false;
13100 EnterExpressionEvaluationContext
Context(
13101 getSema(), EnterExpressionEvaluationContext::InitList
);
13103 SmallVector
<Expr
*, 4> Inits
;
13104 if (getDerived().TransformExprs(E
->getInits(), E
->getNumInits(), false,
13105 Inits
, &InitChanged
))
13106 return ExprError();
13108 if (!getDerived().AlwaysRebuild() && !InitChanged
) {
13109 // FIXME: Attempt to reuse the existing syntactic form of the InitListExpr
13110 // in some cases. We can't reuse it in general, because the syntactic and
13111 // semantic forms are linked, and we can't know that semantic form will
13112 // match even if the syntactic form does.
13115 return getDerived().RebuildInitList(E
->getLBraceLoc(), Inits
,
13116 E
->getRBraceLoc());
13119 template<typename Derived
>
13121 TreeTransform
<Derived
>::TransformDesignatedInitExpr(DesignatedInitExpr
*E
) {
13124 // transform the initializer value
13125 ExprResult Init
= getDerived().TransformExpr(E
->getInit());
13126 if (Init
.isInvalid())
13127 return ExprError();
13129 // transform the designators.
13130 SmallVector
<Expr
*, 4> ArrayExprs
;
13131 bool ExprChanged
= false;
13132 for (const DesignatedInitExpr::Designator
&D
: E
->designators()) {
13133 if (D
.isFieldDesignator()) {
13134 if (D
.getFieldDecl()) {
13135 FieldDecl
*Field
= cast_or_null
<FieldDecl
>(
13136 getDerived().TransformDecl(D
.getFieldLoc(), D
.getFieldDecl()));
13137 if (Field
!= D
.getFieldDecl())
13138 // Rebuild the expression when the transformed FieldDecl is
13139 // different to the already assigned FieldDecl.
13140 ExprChanged
= true;
13141 if (Field
->isAnonymousStructOrUnion())
13144 // Ensure that the designator expression is rebuilt when there isn't
13145 // a resolved FieldDecl in the designator as we don't want to assign
13146 // a FieldDecl to a pattern designator that will be instantiated again.
13147 ExprChanged
= true;
13149 Desig
.AddDesignator(Designator::CreateFieldDesignator(
13150 D
.getFieldName(), D
.getDotLoc(), D
.getFieldLoc()));
13154 if (D
.isArrayDesignator()) {
13155 ExprResult Index
= getDerived().TransformExpr(E
->getArrayIndex(D
));
13156 if (Index
.isInvalid())
13157 return ExprError();
13159 Desig
.AddDesignator(
13160 Designator::CreateArrayDesignator(Index
.get(), D
.getLBracketLoc()));
13162 ExprChanged
= ExprChanged
|| Init
.get() != E
->getArrayIndex(D
);
13163 ArrayExprs
.push_back(Index
.get());
13167 assert(D
.isArrayRangeDesignator() && "New kind of designator?");
13169 = getDerived().TransformExpr(E
->getArrayRangeStart(D
));
13170 if (Start
.isInvalid())
13171 return ExprError();
13173 ExprResult End
= getDerived().TransformExpr(E
->getArrayRangeEnd(D
));
13174 if (End
.isInvalid())
13175 return ExprError();
13177 Desig
.AddDesignator(Designator::CreateArrayRangeDesignator(
13178 Start
.get(), End
.get(), D
.getLBracketLoc(), D
.getEllipsisLoc()));
13180 ExprChanged
= ExprChanged
|| Start
.get() != E
->getArrayRangeStart(D
) ||
13181 End
.get() != E
->getArrayRangeEnd(D
);
13183 ArrayExprs
.push_back(Start
.get());
13184 ArrayExprs
.push_back(End
.get());
13187 if (!getDerived().AlwaysRebuild() &&
13188 Init
.get() == E
->getInit() &&
13192 return getDerived().RebuildDesignatedInitExpr(Desig
, ArrayExprs
,
13193 E
->getEqualOrColonLoc(),
13194 E
->usesGNUSyntax(), Init
.get());
13197 // Seems that if TransformInitListExpr() only works on the syntactic form of an
13198 // InitListExpr, then a DesignatedInitUpdateExpr is not encountered.
13199 template<typename Derived
>
13201 TreeTransform
<Derived
>::TransformDesignatedInitUpdateExpr(
13202 DesignatedInitUpdateExpr
*E
) {
13203 llvm_unreachable("Unexpected DesignatedInitUpdateExpr in syntactic form of "
13205 return ExprError();
13208 template<typename Derived
>
13210 TreeTransform
<Derived
>::TransformNoInitExpr(
13212 llvm_unreachable("Unexpected NoInitExpr in syntactic form of initializer");
13213 return ExprError();
13216 template<typename Derived
>
13218 TreeTransform
<Derived
>::TransformArrayInitLoopExpr(ArrayInitLoopExpr
*E
) {
13219 llvm_unreachable("Unexpected ArrayInitLoopExpr outside of initializer");
13220 return ExprError();
13223 template<typename Derived
>
13225 TreeTransform
<Derived
>::TransformArrayInitIndexExpr(ArrayInitIndexExpr
*E
) {
13226 llvm_unreachable("Unexpected ArrayInitIndexExpr outside of initializer");
13227 return ExprError();
13230 template<typename Derived
>
13232 TreeTransform
<Derived
>::TransformImplicitValueInitExpr(
13233 ImplicitValueInitExpr
*E
) {
13234 TemporaryBase
Rebase(*this, E
->getBeginLoc(), DeclarationName());
13236 // FIXME: Will we ever have proper type location here? Will we actually
13237 // need to transform the type?
13238 QualType T
= getDerived().TransformType(E
->getType());
13240 return ExprError();
13242 if (!getDerived().AlwaysRebuild() &&
13246 return getDerived().RebuildImplicitValueInitExpr(T
);
13249 template<typename Derived
>
13251 TreeTransform
<Derived
>::TransformVAArgExpr(VAArgExpr
*E
) {
13252 TypeSourceInfo
*TInfo
= getDerived().TransformType(E
->getWrittenTypeInfo());
13254 return ExprError();
13256 ExprResult SubExpr
= getDerived().TransformExpr(E
->getSubExpr());
13257 if (SubExpr
.isInvalid())
13258 return ExprError();
13260 if (!getDerived().AlwaysRebuild() &&
13261 TInfo
== E
->getWrittenTypeInfo() &&
13262 SubExpr
.get() == E
->getSubExpr())
13265 return getDerived().RebuildVAArgExpr(E
->getBuiltinLoc(), SubExpr
.get(),
13266 TInfo
, E
->getRParenLoc());
13269 template<typename Derived
>
13271 TreeTransform
<Derived
>::TransformParenListExpr(ParenListExpr
*E
) {
13272 bool ArgumentChanged
= false;
13273 SmallVector
<Expr
*, 4> Inits
;
13274 if (TransformExprs(E
->getExprs(), E
->getNumExprs(), true, Inits
,
13276 return ExprError();
13278 return getDerived().RebuildParenListExpr(E
->getLParenLoc(),
13280 E
->getRParenLoc());
13283 /// Transform an address-of-label expression.
13285 /// By default, the transformation of an address-of-label expression always
13286 /// rebuilds the expression, so that the label identifier can be resolved to
13287 /// the corresponding label statement by semantic analysis.
13288 template<typename Derived
>
13290 TreeTransform
<Derived
>::TransformAddrLabelExpr(AddrLabelExpr
*E
) {
13291 Decl
*LD
= getDerived().TransformDecl(E
->getLabel()->getLocation(),
13294 return ExprError();
13296 return getDerived().RebuildAddrLabelExpr(E
->getAmpAmpLoc(), E
->getLabelLoc(),
13297 cast
<LabelDecl
>(LD
));
13300 template<typename Derived
>
13302 TreeTransform
<Derived
>::TransformStmtExpr(StmtExpr
*E
) {
13303 SemaRef
.ActOnStartStmtExpr();
13305 = getDerived().TransformCompoundStmt(E
->getSubStmt(), true);
13306 if (SubStmt
.isInvalid()) {
13307 SemaRef
.ActOnStmtExprError();
13308 return ExprError();
13311 unsigned OldDepth
= E
->getTemplateDepth();
13312 unsigned NewDepth
= getDerived().TransformTemplateDepth(OldDepth
);
13314 if (!getDerived().AlwaysRebuild() && OldDepth
== NewDepth
&&
13315 SubStmt
.get() == E
->getSubStmt()) {
13316 // Calling this an 'error' is unintuitive, but it does the right thing.
13317 SemaRef
.ActOnStmtExprError();
13318 return SemaRef
.MaybeBindToTemporary(E
);
13321 return getDerived().RebuildStmtExpr(E
->getLParenLoc(), SubStmt
.get(),
13322 E
->getRParenLoc(), NewDepth
);
13325 template<typename Derived
>
13327 TreeTransform
<Derived
>::TransformChooseExpr(ChooseExpr
*E
) {
13328 ExprResult Cond
= getDerived().TransformExpr(E
->getCond());
13329 if (Cond
.isInvalid())
13330 return ExprError();
13332 ExprResult LHS
= getDerived().TransformExpr(E
->getLHS());
13333 if (LHS
.isInvalid())
13334 return ExprError();
13336 ExprResult RHS
= getDerived().TransformExpr(E
->getRHS());
13337 if (RHS
.isInvalid())
13338 return ExprError();
13340 if (!getDerived().AlwaysRebuild() &&
13341 Cond
.get() == E
->getCond() &&
13342 LHS
.get() == E
->getLHS() &&
13343 RHS
.get() == E
->getRHS())
13346 return getDerived().RebuildChooseExpr(E
->getBuiltinLoc(),
13347 Cond
.get(), LHS
.get(), RHS
.get(),
13348 E
->getRParenLoc());
13351 template<typename Derived
>
13353 TreeTransform
<Derived
>::TransformGNUNullExpr(GNUNullExpr
*E
) {
13357 template<typename Derived
>
13359 TreeTransform
<Derived
>::TransformCXXOperatorCallExpr(CXXOperatorCallExpr
*E
) {
13360 switch (E
->getOperator()) {
13364 case OO_Array_Delete
:
13365 llvm_unreachable("new and delete operators cannot use CXXOperatorCallExpr");
13369 // This is a call to an object's operator().
13370 assert(E
->getNumArgs() >= 1 && "Object call is missing arguments");
13372 // Transform the object itself.
13373 ExprResult Object
= getDerived().TransformExpr(E
->getArg(0));
13374 if (Object
.isInvalid())
13375 return ExprError();
13377 // FIXME: Poor location information
13378 SourceLocation FakeLParenLoc
= SemaRef
.getLocForEndOfToken(
13379 static_cast<Expr
*>(Object
.get())->getEndLoc());
13381 // Transform the call arguments.
13382 SmallVector
<Expr
*, 8> Args
;
13383 if (getDerived().TransformExprs(E
->getArgs() + 1, E
->getNumArgs() - 1, true,
13385 return ExprError();
13387 if (E
->getOperator() == OO_Subscript
)
13388 return getDerived().RebuildCxxSubscriptExpr(Object
.get(), FakeLParenLoc
,
13389 Args
, E
->getEndLoc());
13391 return getDerived().RebuildCallExpr(Object
.get(), FakeLParenLoc
, Args
,
13395 #define OVERLOADED_OPERATOR(Name, Spelling, Token, Unary, Binary, MemberOnly) \
13399 #define OVERLOADED_OPERATOR_MULTI(Name,Spelling,Unary,Binary,MemberOnly)
13400 #include "clang/Basic/OperatorKinds.def"
13402 case OO_Conditional
:
13403 llvm_unreachable("conditional operator is not actually overloadable");
13406 case NUM_OVERLOADED_OPERATORS
:
13407 llvm_unreachable("not an overloaded operator?");
13411 if (E
->getNumArgs() == 1 && E
->getOperator() == OO_Amp
)
13412 First
= getDerived().TransformAddressOfOperand(E
->getArg(0));
13414 First
= getDerived().TransformExpr(E
->getArg(0));
13415 if (First
.isInvalid())
13416 return ExprError();
13419 if (E
->getNumArgs() == 2) {
13421 getDerived().TransformInitializer(E
->getArg(1), /*NotCopyInit=*/false);
13422 if (Second
.isInvalid())
13423 return ExprError();
13426 Sema::FPFeaturesStateRAII
FPFeaturesState(getSema());
13427 FPOptionsOverride
NewOverrides(E
->getFPFeatures());
13428 getSema().CurFPFeatures
=
13429 NewOverrides
.applyOverrides(getSema().getLangOpts());
13430 getSema().FpPragmaStack
.CurrentValue
= NewOverrides
;
13432 Expr
*Callee
= E
->getCallee();
13433 if (UnresolvedLookupExpr
*ULE
= dyn_cast
<UnresolvedLookupExpr
>(Callee
)) {
13434 LookupResult
R(SemaRef
, ULE
->getName(), ULE
->getNameLoc(),
13435 Sema::LookupOrdinaryName
);
13436 if (getDerived().TransformOverloadExprDecls(ULE
, ULE
->requiresADL(), R
))
13437 return ExprError();
13439 return getDerived().RebuildCXXOperatorCallExpr(
13440 E
->getOperator(), E
->getOperatorLoc(), Callee
->getBeginLoc(),
13441 ULE
->requiresADL(), R
.asUnresolvedSet(), First
.get(), Second
.get());
13444 UnresolvedSet
<1> Functions
;
13445 if (ImplicitCastExpr
*ICE
= dyn_cast
<ImplicitCastExpr
>(Callee
))
13446 Callee
= ICE
->getSubExprAsWritten();
13447 NamedDecl
*DR
= cast
<DeclRefExpr
>(Callee
)->getDecl();
13448 ValueDecl
*VD
= cast_or_null
<ValueDecl
>(
13449 getDerived().TransformDecl(DR
->getLocation(), DR
));
13451 return ExprError();
13453 if (!isa
<CXXMethodDecl
>(VD
))
13454 Functions
.addDecl(VD
);
13456 return getDerived().RebuildCXXOperatorCallExpr(
13457 E
->getOperator(), E
->getOperatorLoc(), Callee
->getBeginLoc(),
13458 /*RequiresADL=*/false, Functions
, First
.get(), Second
.get());
13461 template<typename Derived
>
13463 TreeTransform
<Derived
>::TransformCXXMemberCallExpr(CXXMemberCallExpr
*E
) {
13464 return getDerived().TransformCallExpr(E
);
13467 template <typename Derived
>
13468 ExprResult TreeTransform
<Derived
>::TransformSourceLocExpr(SourceLocExpr
*E
) {
13469 bool NeedRebuildFunc
= SourceLocExpr::MayBeDependent(E
->getIdentKind()) &&
13470 getSema().CurContext
!= E
->getParentContext();
13472 if (!getDerived().AlwaysRebuild() && !NeedRebuildFunc
)
13475 return getDerived().RebuildSourceLocExpr(E
->getIdentKind(), E
->getType(),
13476 E
->getBeginLoc(), E
->getEndLoc(),
13477 getSema().CurContext
);
13480 template <typename Derived
>
13481 ExprResult TreeTransform
<Derived
>::TransformEmbedExpr(EmbedExpr
*E
) {
13485 template<typename Derived
>
13487 TreeTransform
<Derived
>::TransformCUDAKernelCallExpr(CUDAKernelCallExpr
*E
) {
13488 // Transform the callee.
13489 ExprResult Callee
= getDerived().TransformExpr(E
->getCallee());
13490 if (Callee
.isInvalid())
13491 return ExprError();
13493 // Transform exec config.
13494 ExprResult EC
= getDerived().TransformCallExpr(E
->getConfig());
13495 if (EC
.isInvalid())
13496 return ExprError();
13498 // Transform arguments.
13499 bool ArgChanged
= false;
13500 SmallVector
<Expr
*, 8> Args
;
13501 if (getDerived().TransformExprs(E
->getArgs(), E
->getNumArgs(), true, Args
,
13503 return ExprError();
13505 if (!getDerived().AlwaysRebuild() &&
13506 Callee
.get() == E
->getCallee() &&
13508 return SemaRef
.MaybeBindToTemporary(E
);
13510 // FIXME: Wrong source location information for the '('.
13511 SourceLocation FakeLParenLoc
13512 = ((Expr
*)Callee
.get())->getSourceRange().getBegin();
13513 return getDerived().RebuildCallExpr(Callee
.get(), FakeLParenLoc
,
13515 E
->getRParenLoc(), EC
.get());
13518 template<typename Derived
>
13520 TreeTransform
<Derived
>::TransformCXXNamedCastExpr(CXXNamedCastExpr
*E
) {
13521 TypeSourceInfo
*Type
= getDerived().TransformType(E
->getTypeInfoAsWritten());
13523 return ExprError();
13526 = getDerived().TransformExpr(E
->getSubExprAsWritten());
13527 if (SubExpr
.isInvalid())
13528 return ExprError();
13530 if (!getDerived().AlwaysRebuild() &&
13531 Type
== E
->getTypeInfoAsWritten() &&
13532 SubExpr
.get() == E
->getSubExpr())
13534 return getDerived().RebuildCXXNamedCastExpr(
13535 E
->getOperatorLoc(), E
->getStmtClass(), E
->getAngleBrackets().getBegin(),
13536 Type
, E
->getAngleBrackets().getEnd(),
13537 // FIXME. this should be '(' location
13538 E
->getAngleBrackets().getEnd(), SubExpr
.get(), E
->getRParenLoc());
13541 template<typename Derived
>
13543 TreeTransform
<Derived
>::TransformBuiltinBitCastExpr(BuiltinBitCastExpr
*BCE
) {
13544 TypeSourceInfo
*TSI
=
13545 getDerived().TransformType(BCE
->getTypeInfoAsWritten());
13547 return ExprError();
13549 ExprResult Sub
= getDerived().TransformExpr(BCE
->getSubExpr());
13550 if (Sub
.isInvalid())
13551 return ExprError();
13553 return getDerived().RebuildBuiltinBitCastExpr(BCE
->getBeginLoc(), TSI
,
13554 Sub
.get(), BCE
->getEndLoc());
13557 template<typename Derived
>
13559 TreeTransform
<Derived
>::TransformCXXStaticCastExpr(CXXStaticCastExpr
*E
) {
13560 return getDerived().TransformCXXNamedCastExpr(E
);
13563 template<typename Derived
>
13565 TreeTransform
<Derived
>::TransformCXXDynamicCastExpr(CXXDynamicCastExpr
*E
) {
13566 return getDerived().TransformCXXNamedCastExpr(E
);
13569 template<typename Derived
>
13571 TreeTransform
<Derived
>::TransformCXXReinterpretCastExpr(
13572 CXXReinterpretCastExpr
*E
) {
13573 return getDerived().TransformCXXNamedCastExpr(E
);
13576 template<typename Derived
>
13578 TreeTransform
<Derived
>::TransformCXXConstCastExpr(CXXConstCastExpr
*E
) {
13579 return getDerived().TransformCXXNamedCastExpr(E
);
13582 template<typename Derived
>
13584 TreeTransform
<Derived
>::TransformCXXAddrspaceCastExpr(CXXAddrspaceCastExpr
*E
) {
13585 return getDerived().TransformCXXNamedCastExpr(E
);
13588 template<typename Derived
>
13590 TreeTransform
<Derived
>::TransformCXXFunctionalCastExpr(
13591 CXXFunctionalCastExpr
*E
) {
13592 TypeSourceInfo
*Type
=
13593 getDerived().TransformTypeWithDeducedTST(E
->getTypeInfoAsWritten());
13595 return ExprError();
13598 = getDerived().TransformExpr(E
->getSubExprAsWritten());
13599 if (SubExpr
.isInvalid())
13600 return ExprError();
13602 if (!getDerived().AlwaysRebuild() &&
13603 Type
== E
->getTypeInfoAsWritten() &&
13604 SubExpr
.get() == E
->getSubExpr())
13607 return getDerived().RebuildCXXFunctionalCastExpr(Type
,
13611 E
->isListInitialization());
13614 template<typename Derived
>
13616 TreeTransform
<Derived
>::TransformCXXTypeidExpr(CXXTypeidExpr
*E
) {
13617 if (E
->isTypeOperand()) {
13618 TypeSourceInfo
*TInfo
13619 = getDerived().TransformType(E
->getTypeOperandSourceInfo());
13621 return ExprError();
13623 if (!getDerived().AlwaysRebuild() &&
13624 TInfo
== E
->getTypeOperandSourceInfo())
13627 return getDerived().RebuildCXXTypeidExpr(E
->getType(), E
->getBeginLoc(),
13628 TInfo
, E
->getEndLoc());
13631 // Typeid's operand is an unevaluated context, unless it's a polymorphic
13632 // type. We must not unilaterally enter unevaluated context here, as then
13633 // semantic processing can re-transform an already transformed operand.
13634 Expr
*Op
= E
->getExprOperand();
13635 auto EvalCtx
= Sema::ExpressionEvaluationContext::Unevaluated
;
13636 if (E
->isGLValue())
13637 if (auto *RecordT
= Op
->getType()->getAs
<RecordType
>())
13638 if (cast
<CXXRecordDecl
>(RecordT
->getDecl())->isPolymorphic())
13639 EvalCtx
= SemaRef
.ExprEvalContexts
.back().Context
;
13641 EnterExpressionEvaluationContext
Unevaluated(SemaRef
, EvalCtx
,
13642 Sema::ReuseLambdaContextDecl
);
13644 ExprResult SubExpr
= getDerived().TransformExpr(Op
);
13645 if (SubExpr
.isInvalid())
13646 return ExprError();
13648 if (!getDerived().AlwaysRebuild() &&
13649 SubExpr
.get() == E
->getExprOperand())
13652 return getDerived().RebuildCXXTypeidExpr(E
->getType(), E
->getBeginLoc(),
13653 SubExpr
.get(), E
->getEndLoc());
13656 template<typename Derived
>
13658 TreeTransform
<Derived
>::TransformCXXUuidofExpr(CXXUuidofExpr
*E
) {
13659 if (E
->isTypeOperand()) {
13660 TypeSourceInfo
*TInfo
13661 = getDerived().TransformType(E
->getTypeOperandSourceInfo());
13663 return ExprError();
13665 if (!getDerived().AlwaysRebuild() &&
13666 TInfo
== E
->getTypeOperandSourceInfo())
13669 return getDerived().RebuildCXXUuidofExpr(E
->getType(), E
->getBeginLoc(),
13670 TInfo
, E
->getEndLoc());
13673 EnterExpressionEvaluationContext
Unevaluated(
13674 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
);
13676 ExprResult SubExpr
= getDerived().TransformExpr(E
->getExprOperand());
13677 if (SubExpr
.isInvalid())
13678 return ExprError();
13680 if (!getDerived().AlwaysRebuild() &&
13681 SubExpr
.get() == E
->getExprOperand())
13684 return getDerived().RebuildCXXUuidofExpr(E
->getType(), E
->getBeginLoc(),
13685 SubExpr
.get(), E
->getEndLoc());
13688 template<typename Derived
>
13690 TreeTransform
<Derived
>::TransformCXXBoolLiteralExpr(CXXBoolLiteralExpr
*E
) {
13694 template<typename Derived
>
13696 TreeTransform
<Derived
>::TransformCXXNullPtrLiteralExpr(
13697 CXXNullPtrLiteralExpr
*E
) {
13701 template<typename Derived
>
13703 TreeTransform
<Derived
>::TransformCXXThisExpr(CXXThisExpr
*E
) {
13705 // In lambdas, the qualifiers of the type depends of where in
13706 // the call operator `this` appear, and we do not have a good way to
13707 // rebuild this information, so we transform the type.
13709 // In other contexts, the type of `this` may be overrided
13710 // for type deduction, so we need to recompute it.
13712 // Always recompute the type if we're in the body of a lambda, and
13713 // 'this' is dependent on a lambda's explicit object parameter.
13714 QualType T
= [&]() {
13715 auto &S
= getSema();
13716 if (E
->isCapturedByCopyInLambdaWithExplicitObjectParameter())
13717 return S
.getCurrentThisType();
13718 if (S
.getCurLambda())
13719 return getDerived().TransformType(E
->getType());
13720 return S
.getCurrentThisType();
13723 if (!getDerived().AlwaysRebuild() && T
== E
->getType()) {
13724 // Mark it referenced in the new context regardless.
13725 // FIXME: this is a bit instantiation-specific.
13726 getSema().MarkThisReferenced(E
);
13730 return getDerived().RebuildCXXThisExpr(E
->getBeginLoc(), T
, E
->isImplicit());
13733 template<typename Derived
>
13735 TreeTransform
<Derived
>::TransformCXXThrowExpr(CXXThrowExpr
*E
) {
13736 ExprResult SubExpr
= getDerived().TransformExpr(E
->getSubExpr());
13737 if (SubExpr
.isInvalid())
13738 return ExprError();
13740 if (!getDerived().AlwaysRebuild() &&
13741 SubExpr
.get() == E
->getSubExpr())
13744 return getDerived().RebuildCXXThrowExpr(E
->getThrowLoc(), SubExpr
.get(),
13745 E
->isThrownVariableInScope());
13748 template<typename Derived
>
13750 TreeTransform
<Derived
>::TransformCXXDefaultArgExpr(CXXDefaultArgExpr
*E
) {
13751 ParmVarDecl
*Param
= cast_or_null
<ParmVarDecl
>(
13752 getDerived().TransformDecl(E
->getBeginLoc(), E
->getParam()));
13754 return ExprError();
13756 ExprResult InitRes
;
13757 if (E
->hasRewrittenInit()) {
13758 InitRes
= getDerived().TransformExpr(E
->getRewrittenExpr());
13759 if (InitRes
.isInvalid())
13760 return ExprError();
13763 if (!getDerived().AlwaysRebuild() && Param
== E
->getParam() &&
13764 E
->getUsedContext() == SemaRef
.CurContext
&&
13765 InitRes
.get() == E
->getRewrittenExpr())
13768 return getDerived().RebuildCXXDefaultArgExpr(E
->getUsedLocation(), Param
,
13772 template<typename Derived
>
13774 TreeTransform
<Derived
>::TransformCXXDefaultInitExpr(CXXDefaultInitExpr
*E
) {
13775 FieldDecl
*Field
= cast_or_null
<FieldDecl
>(
13776 getDerived().TransformDecl(E
->getBeginLoc(), E
->getField()));
13778 return ExprError();
13780 if (!getDerived().AlwaysRebuild() && Field
== E
->getField() &&
13781 E
->getUsedContext() == SemaRef
.CurContext
)
13784 return getDerived().RebuildCXXDefaultInitExpr(E
->getExprLoc(), Field
);
13787 template<typename Derived
>
13789 TreeTransform
<Derived
>::TransformCXXScalarValueInitExpr(
13790 CXXScalarValueInitExpr
*E
) {
13791 TypeSourceInfo
*T
= getDerived().TransformType(E
->getTypeSourceInfo());
13793 return ExprError();
13795 if (!getDerived().AlwaysRebuild() &&
13796 T
== E
->getTypeSourceInfo())
13799 return getDerived().RebuildCXXScalarValueInitExpr(T
,
13800 /*FIXME:*/T
->getTypeLoc().getEndLoc(),
13801 E
->getRParenLoc());
13804 template<typename Derived
>
13806 TreeTransform
<Derived
>::TransformCXXNewExpr(CXXNewExpr
*E
) {
13807 // Transform the type that we're allocating
13808 TypeSourceInfo
*AllocTypeInfo
=
13809 getDerived().TransformTypeWithDeducedTST(E
->getAllocatedTypeSourceInfo());
13810 if (!AllocTypeInfo
)
13811 return ExprError();
13813 // Transform the size of the array we're allocating (if any).
13814 std::optional
<Expr
*> ArraySize
;
13815 if (E
->isArray()) {
13816 ExprResult NewArraySize
;
13817 if (std::optional
<Expr
*> OldArraySize
= E
->getArraySize()) {
13818 NewArraySize
= getDerived().TransformExpr(*OldArraySize
);
13819 if (NewArraySize
.isInvalid())
13820 return ExprError();
13822 ArraySize
= NewArraySize
.get();
13825 // Transform the placement arguments (if any).
13826 bool ArgumentChanged
= false;
13827 SmallVector
<Expr
*, 8> PlacementArgs
;
13828 if (getDerived().TransformExprs(E
->getPlacementArgs(),
13829 E
->getNumPlacementArgs(), true,
13830 PlacementArgs
, &ArgumentChanged
))
13831 return ExprError();
13833 // Transform the initializer (if any).
13834 Expr
*OldInit
= E
->getInitializer();
13835 ExprResult NewInit
;
13837 NewInit
= getDerived().TransformInitializer(OldInit
, true);
13838 if (NewInit
.isInvalid())
13839 return ExprError();
13841 // Transform new operator and delete operator.
13842 FunctionDecl
*OperatorNew
= nullptr;
13843 if (E
->getOperatorNew()) {
13844 OperatorNew
= cast_or_null
<FunctionDecl
>(
13845 getDerived().TransformDecl(E
->getBeginLoc(), E
->getOperatorNew()));
13847 return ExprError();
13850 FunctionDecl
*OperatorDelete
= nullptr;
13851 if (E
->getOperatorDelete()) {
13852 OperatorDelete
= cast_or_null
<FunctionDecl
>(
13853 getDerived().TransformDecl(E
->getBeginLoc(), E
->getOperatorDelete()));
13854 if (!OperatorDelete
)
13855 return ExprError();
13858 if (!getDerived().AlwaysRebuild() &&
13859 AllocTypeInfo
== E
->getAllocatedTypeSourceInfo() &&
13860 ArraySize
== E
->getArraySize() &&
13861 NewInit
.get() == OldInit
&&
13862 OperatorNew
== E
->getOperatorNew() &&
13863 OperatorDelete
== E
->getOperatorDelete() &&
13864 !ArgumentChanged
) {
13865 // Mark any declarations we need as referenced.
13866 // FIXME: instantiation-specific.
13868 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(), OperatorNew
);
13869 if (OperatorDelete
)
13870 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(), OperatorDelete
);
13872 if (E
->isArray() && !E
->getAllocatedType()->isDependentType()) {
13873 QualType ElementType
13874 = SemaRef
.Context
.getBaseElementType(E
->getAllocatedType());
13875 if (const RecordType
*RecordT
= ElementType
->getAs
<RecordType
>()) {
13876 CXXRecordDecl
*Record
= cast
<CXXRecordDecl
>(RecordT
->getDecl());
13877 if (CXXDestructorDecl
*Destructor
= SemaRef
.LookupDestructor(Record
)) {
13878 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(), Destructor
);
13886 QualType AllocType
= AllocTypeInfo
->getType();
13888 // If no array size was specified, but the new expression was
13889 // instantiated with an array type (e.g., "new T" where T is
13890 // instantiated with "int[4]"), extract the outer bound from the
13891 // array type as our array size. We do this with constant and
13892 // dependently-sized array types.
13893 const ArrayType
*ArrayT
= SemaRef
.Context
.getAsArrayType(AllocType
);
13896 } else if (const ConstantArrayType
*ConsArrayT
13897 = dyn_cast
<ConstantArrayType
>(ArrayT
)) {
13898 ArraySize
= IntegerLiteral::Create(SemaRef
.Context
, ConsArrayT
->getSize(),
13899 SemaRef
.Context
.getSizeType(),
13900 /*FIXME:*/ E
->getBeginLoc());
13901 AllocType
= ConsArrayT
->getElementType();
13902 } else if (const DependentSizedArrayType
*DepArrayT
13903 = dyn_cast
<DependentSizedArrayType
>(ArrayT
)) {
13904 if (DepArrayT
->getSizeExpr()) {
13905 ArraySize
= DepArrayT
->getSizeExpr();
13906 AllocType
= DepArrayT
->getElementType();
13911 return getDerived().RebuildCXXNewExpr(
13912 E
->getBeginLoc(), E
->isGlobalNew(),
13913 /*FIXME:*/ E
->getBeginLoc(), PlacementArgs
,
13914 /*FIXME:*/ E
->getBeginLoc(), E
->getTypeIdParens(), AllocType
,
13915 AllocTypeInfo
, ArraySize
, E
->getDirectInitRange(), NewInit
.get());
13918 template<typename Derived
>
13920 TreeTransform
<Derived
>::TransformCXXDeleteExpr(CXXDeleteExpr
*E
) {
13921 ExprResult Operand
= getDerived().TransformExpr(E
->getArgument());
13922 if (Operand
.isInvalid())
13923 return ExprError();
13925 // Transform the delete operator, if known.
13926 FunctionDecl
*OperatorDelete
= nullptr;
13927 if (E
->getOperatorDelete()) {
13928 OperatorDelete
= cast_or_null
<FunctionDecl
>(
13929 getDerived().TransformDecl(E
->getBeginLoc(), E
->getOperatorDelete()));
13930 if (!OperatorDelete
)
13931 return ExprError();
13934 if (!getDerived().AlwaysRebuild() &&
13935 Operand
.get() == E
->getArgument() &&
13936 OperatorDelete
== E
->getOperatorDelete()) {
13937 // Mark any declarations we need as referenced.
13938 // FIXME: instantiation-specific.
13939 if (OperatorDelete
)
13940 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(), OperatorDelete
);
13942 if (!E
->getArgument()->isTypeDependent()) {
13943 QualType Destroyed
= SemaRef
.Context
.getBaseElementType(
13944 E
->getDestroyedType());
13945 if (const RecordType
*DestroyedRec
= Destroyed
->getAs
<RecordType
>()) {
13946 CXXRecordDecl
*Record
= cast
<CXXRecordDecl
>(DestroyedRec
->getDecl());
13947 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(),
13948 SemaRef
.LookupDestructor(Record
));
13955 return getDerived().RebuildCXXDeleteExpr(
13956 E
->getBeginLoc(), E
->isGlobalDelete(), E
->isArrayForm(), Operand
.get());
13959 template<typename Derived
>
13961 TreeTransform
<Derived
>::TransformCXXPseudoDestructorExpr(
13962 CXXPseudoDestructorExpr
*E
) {
13963 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
13964 if (Base
.isInvalid())
13965 return ExprError();
13967 ParsedType ObjectTypePtr
;
13968 bool MayBePseudoDestructor
= false;
13969 Base
= SemaRef
.ActOnStartCXXMemberReference(nullptr, Base
.get(),
13970 E
->getOperatorLoc(),
13971 E
->isArrow()? tok::arrow
: tok::period
,
13973 MayBePseudoDestructor
);
13974 if (Base
.isInvalid())
13975 return ExprError();
13977 QualType ObjectType
= ObjectTypePtr
.get();
13978 NestedNameSpecifierLoc QualifierLoc
= E
->getQualifierLoc();
13979 if (QualifierLoc
) {
13981 = getDerived().TransformNestedNameSpecifierLoc(QualifierLoc
, ObjectType
);
13983 return ExprError();
13986 SS
.Adopt(QualifierLoc
);
13988 PseudoDestructorTypeStorage Destroyed
;
13989 if (E
->getDestroyedTypeInfo()) {
13990 TypeSourceInfo
*DestroyedTypeInfo
13991 = getDerived().TransformTypeInObjectScope(E
->getDestroyedTypeInfo(),
13992 ObjectType
, nullptr, SS
);
13993 if (!DestroyedTypeInfo
)
13994 return ExprError();
13995 Destroyed
= DestroyedTypeInfo
;
13996 } else if (!ObjectType
.isNull() && ObjectType
->isDependentType()) {
13997 // We aren't likely to be able to resolve the identifier down to a type
13998 // now anyway, so just retain the identifier.
13999 Destroyed
= PseudoDestructorTypeStorage(E
->getDestroyedTypeIdentifier(),
14000 E
->getDestroyedTypeLoc());
14002 // Look for a destructor known with the given name.
14003 ParsedType T
= SemaRef
.getDestructorName(
14004 *E
->getDestroyedTypeIdentifier(), E
->getDestroyedTypeLoc(),
14005 /*Scope=*/nullptr, SS
, ObjectTypePtr
, false);
14007 return ExprError();
14010 = SemaRef
.Context
.getTrivialTypeSourceInfo(SemaRef
.GetTypeFromParser(T
),
14011 E
->getDestroyedTypeLoc());
14014 TypeSourceInfo
*ScopeTypeInfo
= nullptr;
14015 if (E
->getScopeTypeInfo()) {
14016 CXXScopeSpec EmptySS
;
14017 ScopeTypeInfo
= getDerived().TransformTypeInObjectScope(
14018 E
->getScopeTypeInfo(), ObjectType
, nullptr, EmptySS
);
14019 if (!ScopeTypeInfo
)
14020 return ExprError();
14023 return getDerived().RebuildCXXPseudoDestructorExpr(Base
.get(),
14024 E
->getOperatorLoc(),
14028 E
->getColonColonLoc(),
14033 template <typename Derived
>
14034 bool TreeTransform
<Derived
>::TransformOverloadExprDecls(OverloadExpr
*Old
,
14037 // Transform all the decls.
14038 bool AllEmptyPacks
= true;
14039 for (auto *OldD
: Old
->decls()) {
14040 Decl
*InstD
= getDerived().TransformDecl(Old
->getNameLoc(), OldD
);
14042 // Silently ignore these if a UsingShadowDecl instantiated to nothing.
14043 // This can happen because of dependent hiding.
14044 if (isa
<UsingShadowDecl
>(OldD
))
14052 // Expand using pack declarations.
14053 NamedDecl
*SingleDecl
= cast
<NamedDecl
>(InstD
);
14054 ArrayRef
<NamedDecl
*> Decls
= SingleDecl
;
14055 if (auto *UPD
= dyn_cast
<UsingPackDecl
>(InstD
))
14056 Decls
= UPD
->expansions();
14058 // Expand using declarations.
14059 for (auto *D
: Decls
) {
14060 if (auto *UD
= dyn_cast
<UsingDecl
>(D
)) {
14061 for (auto *SD
: UD
->shadows())
14068 AllEmptyPacks
&= Decls
.empty();
14071 // C++ [temp.res]/8.4.2:
14072 // The program is ill-formed, no diagnostic required, if [...] lookup for
14073 // a name in the template definition found a using-declaration, but the
14074 // lookup in the corresponding scope in the instantiation odoes not find
14075 // any declarations because the using-declaration was a pack expansion and
14076 // the corresponding pack is empty
14077 if (AllEmptyPacks
&& !RequiresADL
) {
14078 getSema().Diag(Old
->getNameLoc(), diag::err_using_pack_expansion_empty
)
14079 << isa
<UnresolvedMemberExpr
>(Old
) << Old
->getName();
14083 // Resolve a kind, but don't do any further analysis. If it's
14084 // ambiguous, the callee needs to deal with it.
14087 if (Old
->hasTemplateKeyword() && !R
.empty()) {
14088 NamedDecl
*FoundDecl
= R
.getRepresentativeDecl()->getUnderlyingDecl();
14089 getSema().FilterAcceptableTemplateNames(R
,
14090 /*AllowFunctionTemplates=*/true,
14091 /*AllowDependent=*/true);
14093 // If a 'template' keyword was used, a lookup that finds only non-template
14094 // names is an error.
14095 getSema().Diag(R
.getNameLoc(),
14096 diag::err_template_kw_refers_to_non_template
)
14097 << R
.getLookupName() << Old
->getQualifierLoc().getSourceRange()
14098 << Old
->hasTemplateKeyword() << Old
->getTemplateKeywordLoc();
14099 getSema().Diag(FoundDecl
->getLocation(),
14100 diag::note_template_kw_refers_to_non_template
)
14101 << R
.getLookupName();
14109 template <typename Derived
>
14110 ExprResult TreeTransform
<Derived
>::TransformUnresolvedLookupExpr(
14111 UnresolvedLookupExpr
*Old
) {
14112 return TransformUnresolvedLookupExpr(Old
, /*IsAddressOfOperand=*/false);
14115 template <typename Derived
>
14117 TreeTransform
<Derived
>::TransformUnresolvedLookupExpr(UnresolvedLookupExpr
*Old
,
14118 bool IsAddressOfOperand
) {
14119 LookupResult
R(SemaRef
, Old
->getName(), Old
->getNameLoc(),
14120 Sema::LookupOrdinaryName
);
14122 // Transform the declaration set.
14123 if (TransformOverloadExprDecls(Old
, Old
->requiresADL(), R
))
14124 return ExprError();
14126 // Rebuild the nested-name qualifier, if present.
14128 if (Old
->getQualifierLoc()) {
14129 NestedNameSpecifierLoc QualifierLoc
14130 = getDerived().TransformNestedNameSpecifierLoc(Old
->getQualifierLoc());
14132 return ExprError();
14134 SS
.Adopt(QualifierLoc
);
14137 if (Old
->getNamingClass()) {
14138 CXXRecordDecl
*NamingClass
14139 = cast_or_null
<CXXRecordDecl
>(getDerived().TransformDecl(
14141 Old
->getNamingClass()));
14142 if (!NamingClass
) {
14144 return ExprError();
14147 R
.setNamingClass(NamingClass
);
14150 // Rebuild the template arguments, if any.
14151 SourceLocation TemplateKWLoc
= Old
->getTemplateKeywordLoc();
14152 TemplateArgumentListInfo
TransArgs(Old
->getLAngleLoc(), Old
->getRAngleLoc());
14153 if (Old
->hasExplicitTemplateArgs() &&
14154 getDerived().TransformTemplateArguments(Old
->getTemplateArgs(),
14155 Old
->getNumTemplateArgs(),
14158 return ExprError();
14161 // An UnresolvedLookupExpr can refer to a class member. This occurs e.g. when
14162 // a non-static data member is named in an unevaluated operand, or when
14163 // a member is named in a dependent class scope function template explicit
14164 // specialization that is neither declared static nor with an explicit object
14166 if (SemaRef
.isPotentialImplicitMemberAccess(SS
, R
, IsAddressOfOperand
))
14167 return SemaRef
.BuildPossibleImplicitMemberExpr(
14168 SS
, TemplateKWLoc
, R
,
14169 Old
->hasExplicitTemplateArgs() ? &TransArgs
: nullptr,
14172 // If we have neither explicit template arguments, nor the template keyword,
14173 // it's a normal declaration name or member reference.
14174 if (!Old
->hasExplicitTemplateArgs() && !TemplateKWLoc
.isValid())
14175 return getDerived().RebuildDeclarationNameExpr(SS
, R
, Old
->requiresADL());
14177 // If we have template arguments, then rebuild the template-id expression.
14178 return getDerived().RebuildTemplateIdExpr(SS
, TemplateKWLoc
, R
,
14179 Old
->requiresADL(), &TransArgs
);
14182 template<typename Derived
>
14184 TreeTransform
<Derived
>::TransformTypeTraitExpr(TypeTraitExpr
*E
) {
14185 bool ArgChanged
= false;
14186 SmallVector
<TypeSourceInfo
*, 4> Args
;
14187 for (unsigned I
= 0, N
= E
->getNumArgs(); I
!= N
; ++I
) {
14188 TypeSourceInfo
*From
= E
->getArg(I
);
14189 TypeLoc FromTL
= From
->getTypeLoc();
14190 if (!FromTL
.getAs
<PackExpansionTypeLoc
>()) {
14191 TypeLocBuilder TLB
;
14192 TLB
.reserve(FromTL
.getFullDataSize());
14193 QualType To
= getDerived().TransformType(TLB
, FromTL
);
14195 return ExprError();
14197 if (To
== From
->getType())
14198 Args
.push_back(From
);
14200 Args
.push_back(TLB
.getTypeSourceInfo(SemaRef
.Context
, To
));
14208 // We have a pack expansion. Instantiate it.
14209 PackExpansionTypeLoc ExpansionTL
= FromTL
.castAs
<PackExpansionTypeLoc
>();
14210 TypeLoc PatternTL
= ExpansionTL
.getPatternLoc();
14211 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
14212 SemaRef
.collectUnexpandedParameterPacks(PatternTL
, Unexpanded
);
14214 // Determine whether the set of unexpanded parameter packs can and should
14216 bool Expand
= true;
14217 bool RetainExpansion
= false;
14218 std::optional
<unsigned> OrigNumExpansions
=
14219 ExpansionTL
.getTypePtr()->getNumExpansions();
14220 std::optional
<unsigned> NumExpansions
= OrigNumExpansions
;
14221 if (getDerived().TryExpandParameterPacks(ExpansionTL
.getEllipsisLoc(),
14222 PatternTL
.getSourceRange(),
14224 Expand
, RetainExpansion
,
14226 return ExprError();
14229 // The transform has determined that we should perform a simple
14230 // transformation on the pack expansion, producing another pack
14232 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
14234 TypeLocBuilder TLB
;
14235 TLB
.reserve(From
->getTypeLoc().getFullDataSize());
14237 QualType To
= getDerived().TransformType(TLB
, PatternTL
);
14239 return ExprError();
14241 To
= getDerived().RebuildPackExpansionType(To
,
14242 PatternTL
.getSourceRange(),
14243 ExpansionTL
.getEllipsisLoc(),
14246 return ExprError();
14248 PackExpansionTypeLoc ToExpansionTL
14249 = TLB
.push
<PackExpansionTypeLoc
>(To
);
14250 ToExpansionTL
.setEllipsisLoc(ExpansionTL
.getEllipsisLoc());
14251 Args
.push_back(TLB
.getTypeSourceInfo(SemaRef
.Context
, To
));
14255 // Expand the pack expansion by substituting for each argument in the
14257 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
14258 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(SemaRef
, I
);
14259 TypeLocBuilder TLB
;
14260 TLB
.reserve(PatternTL
.getFullDataSize());
14261 QualType To
= getDerived().TransformType(TLB
, PatternTL
);
14263 return ExprError();
14265 if (To
->containsUnexpandedParameterPack()) {
14266 To
= getDerived().RebuildPackExpansionType(To
,
14267 PatternTL
.getSourceRange(),
14268 ExpansionTL
.getEllipsisLoc(),
14271 return ExprError();
14273 PackExpansionTypeLoc ToExpansionTL
14274 = TLB
.push
<PackExpansionTypeLoc
>(To
);
14275 ToExpansionTL
.setEllipsisLoc(ExpansionTL
.getEllipsisLoc());
14278 Args
.push_back(TLB
.getTypeSourceInfo(SemaRef
.Context
, To
));
14281 if (!RetainExpansion
)
14284 // If we're supposed to retain a pack expansion, do so by temporarily
14285 // forgetting the partially-substituted parameter pack.
14286 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
14288 TypeLocBuilder TLB
;
14289 TLB
.reserve(From
->getTypeLoc().getFullDataSize());
14291 QualType To
= getDerived().TransformType(TLB
, PatternTL
);
14293 return ExprError();
14295 To
= getDerived().RebuildPackExpansionType(To
,
14296 PatternTL
.getSourceRange(),
14297 ExpansionTL
.getEllipsisLoc(),
14300 return ExprError();
14302 PackExpansionTypeLoc ToExpansionTL
14303 = TLB
.push
<PackExpansionTypeLoc
>(To
);
14304 ToExpansionTL
.setEllipsisLoc(ExpansionTL
.getEllipsisLoc());
14305 Args
.push_back(TLB
.getTypeSourceInfo(SemaRef
.Context
, To
));
14308 if (!getDerived().AlwaysRebuild() && !ArgChanged
)
14311 return getDerived().RebuildTypeTrait(E
->getTrait(), E
->getBeginLoc(), Args
,
14315 template<typename Derived
>
14317 TreeTransform
<Derived
>::TransformConceptSpecializationExpr(
14318 ConceptSpecializationExpr
*E
) {
14319 const ASTTemplateArgumentListInfo
*Old
= E
->getTemplateArgsAsWritten();
14320 TemplateArgumentListInfo
TransArgs(Old
->LAngleLoc
, Old
->RAngleLoc
);
14321 if (getDerived().TransformTemplateArguments(Old
->getTemplateArgs(),
14322 Old
->NumTemplateArgs
, TransArgs
))
14323 return ExprError();
14325 return getDerived().RebuildConceptSpecializationExpr(
14326 E
->getNestedNameSpecifierLoc(), E
->getTemplateKWLoc(),
14327 E
->getConceptNameInfo(), E
->getFoundDecl(), E
->getNamedConcept(),
14331 template<typename Derived
>
14333 TreeTransform
<Derived
>::TransformRequiresExpr(RequiresExpr
*E
) {
14334 SmallVector
<ParmVarDecl
*, 4> TransParams
;
14335 SmallVector
<QualType
, 4> TransParamTypes
;
14336 Sema::ExtParameterInfoBuilder ExtParamInfos
;
14338 // C++2a [expr.prim.req]p2
14339 // Expressions appearing within a requirement-body are unevaluated operands.
14340 EnterExpressionEvaluationContext
Ctx(
14341 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
,
14342 Sema::ReuseLambdaContextDecl
);
14344 RequiresExprBodyDecl
*Body
= RequiresExprBodyDecl::Create(
14345 getSema().Context
, getSema().CurContext
,
14346 E
->getBody()->getBeginLoc());
14348 Sema::ContextRAII
SavedContext(getSema(), Body
, /*NewThisContext*/false);
14350 ExprResult TypeParamResult
= getDerived().TransformRequiresTypeParams(
14351 E
->getRequiresKWLoc(), E
->getRBraceLoc(), E
, Body
,
14352 E
->getLocalParameters(), TransParamTypes
, TransParams
, ExtParamInfos
);
14354 for (ParmVarDecl
*Param
: TransParams
)
14356 Param
->setDeclContext(Body
);
14358 // On failure to transform, TransformRequiresTypeParams returns an expression
14359 // in the event that the transformation of the type params failed in some way.
14360 // It is expected that this will result in a 'not satisfied' Requires clause
14361 // when instantiating.
14362 if (!TypeParamResult
.isUnset())
14363 return TypeParamResult
;
14365 SmallVector
<concepts::Requirement
*, 4> TransReqs
;
14366 if (getDerived().TransformRequiresExprRequirements(E
->getRequirements(),
14368 return ExprError();
14370 for (concepts::Requirement
*Req
: TransReqs
) {
14371 if (auto *ER
= dyn_cast
<concepts::ExprRequirement
>(Req
)) {
14372 if (ER
->getReturnTypeRequirement().isTypeConstraint()) {
14373 ER
->getReturnTypeRequirement()
14374 .getTypeConstraintTemplateParameterList()->getParam(0)
14375 ->setDeclContext(Body
);
14380 return getDerived().RebuildRequiresExpr(
14381 E
->getRequiresKWLoc(), Body
, E
->getLParenLoc(), TransParams
,
14382 E
->getRParenLoc(), TransReqs
, E
->getRBraceLoc());
14385 template<typename Derived
>
14386 bool TreeTransform
<Derived
>::TransformRequiresExprRequirements(
14387 ArrayRef
<concepts::Requirement
*> Reqs
,
14388 SmallVectorImpl
<concepts::Requirement
*> &Transformed
) {
14389 for (concepts::Requirement
*Req
: Reqs
) {
14390 concepts::Requirement
*TransReq
= nullptr;
14391 if (auto *TypeReq
= dyn_cast
<concepts::TypeRequirement
>(Req
))
14392 TransReq
= getDerived().TransformTypeRequirement(TypeReq
);
14393 else if (auto *ExprReq
= dyn_cast
<concepts::ExprRequirement
>(Req
))
14394 TransReq
= getDerived().TransformExprRequirement(ExprReq
);
14396 TransReq
= getDerived().TransformNestedRequirement(
14397 cast
<concepts::NestedRequirement
>(Req
));
14400 Transformed
.push_back(TransReq
);
14405 template<typename Derived
>
14406 concepts::TypeRequirement
*
14407 TreeTransform
<Derived
>::TransformTypeRequirement(
14408 concepts::TypeRequirement
*Req
) {
14409 if (Req
->isSubstitutionFailure()) {
14410 if (getDerived().AlwaysRebuild())
14411 return getDerived().RebuildTypeRequirement(
14412 Req
->getSubstitutionDiagnostic());
14415 TypeSourceInfo
*TransType
= getDerived().TransformType(Req
->getType());
14418 return getDerived().RebuildTypeRequirement(TransType
);
14421 template<typename Derived
>
14422 concepts::ExprRequirement
*
14423 TreeTransform
<Derived
>::TransformExprRequirement(concepts::ExprRequirement
*Req
) {
14424 llvm::PointerUnion
<Expr
*, concepts::Requirement::SubstitutionDiagnostic
*> TransExpr
;
14425 if (Req
->isExprSubstitutionFailure())
14426 TransExpr
= Req
->getExprSubstitutionDiagnostic();
14428 ExprResult TransExprRes
= getDerived().TransformExpr(Req
->getExpr());
14429 if (TransExprRes
.isUsable() && TransExprRes
.get()->hasPlaceholderType())
14430 TransExprRes
= SemaRef
.CheckPlaceholderExpr(TransExprRes
.get());
14431 if (TransExprRes
.isInvalid())
14433 TransExpr
= TransExprRes
.get();
14436 std::optional
<concepts::ExprRequirement::ReturnTypeRequirement
> TransRetReq
;
14437 const auto &RetReq
= Req
->getReturnTypeRequirement();
14438 if (RetReq
.isEmpty())
14439 TransRetReq
.emplace();
14440 else if (RetReq
.isSubstitutionFailure())
14441 TransRetReq
.emplace(RetReq
.getSubstitutionDiagnostic());
14442 else if (RetReq
.isTypeConstraint()) {
14443 TemplateParameterList
*OrigTPL
=
14444 RetReq
.getTypeConstraintTemplateParameterList();
14445 TemplateParameterList
*TPL
=
14446 getDerived().TransformTemplateParameterList(OrigTPL
);
14449 TransRetReq
.emplace(TPL
);
14451 assert(TransRetReq
&& "All code paths leading here must set TransRetReq");
14452 if (Expr
*E
= TransExpr
.dyn_cast
<Expr
*>())
14453 return getDerived().RebuildExprRequirement(E
, Req
->isSimple(),
14454 Req
->getNoexceptLoc(),
14455 std::move(*TransRetReq
));
14456 return getDerived().RebuildExprRequirement(
14457 cast
<concepts::Requirement::SubstitutionDiagnostic
*>(TransExpr
),
14458 Req
->isSimple(), Req
->getNoexceptLoc(), std::move(*TransRetReq
));
14461 template<typename Derived
>
14462 concepts::NestedRequirement
*
14463 TreeTransform
<Derived
>::TransformNestedRequirement(
14464 concepts::NestedRequirement
*Req
) {
14465 if (Req
->hasInvalidConstraint()) {
14466 if (getDerived().AlwaysRebuild())
14467 return getDerived().RebuildNestedRequirement(
14468 Req
->getInvalidConstraintEntity(), Req
->getConstraintSatisfaction());
14471 ExprResult TransConstraint
=
14472 getDerived().TransformExpr(Req
->getConstraintExpr());
14473 if (TransConstraint
.isInvalid())
14475 return getDerived().RebuildNestedRequirement(TransConstraint
.get());
14478 template<typename Derived
>
14480 TreeTransform
<Derived
>::TransformArrayTypeTraitExpr(ArrayTypeTraitExpr
*E
) {
14481 TypeSourceInfo
*T
= getDerived().TransformType(E
->getQueriedTypeSourceInfo());
14483 return ExprError();
14485 if (!getDerived().AlwaysRebuild() &&
14486 T
== E
->getQueriedTypeSourceInfo())
14489 ExprResult SubExpr
;
14491 EnterExpressionEvaluationContext
Unevaluated(
14492 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
);
14493 SubExpr
= getDerived().TransformExpr(E
->getDimensionExpression());
14494 if (SubExpr
.isInvalid())
14495 return ExprError();
14497 if (!getDerived().AlwaysRebuild() && SubExpr
.get() == E
->getDimensionExpression())
14501 return getDerived().RebuildArrayTypeTrait(E
->getTrait(), E
->getBeginLoc(), T
,
14502 SubExpr
.get(), E
->getEndLoc());
14505 template<typename Derived
>
14507 TreeTransform
<Derived
>::TransformExpressionTraitExpr(ExpressionTraitExpr
*E
) {
14508 ExprResult SubExpr
;
14510 EnterExpressionEvaluationContext
Unevaluated(
14511 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
);
14512 SubExpr
= getDerived().TransformExpr(E
->getQueriedExpression());
14513 if (SubExpr
.isInvalid())
14514 return ExprError();
14516 if (!getDerived().AlwaysRebuild() && SubExpr
.get() == E
->getQueriedExpression())
14520 return getDerived().RebuildExpressionTrait(E
->getTrait(), E
->getBeginLoc(),
14521 SubExpr
.get(), E
->getEndLoc());
14524 template <typename Derived
>
14525 ExprResult TreeTransform
<Derived
>::TransformParenDependentScopeDeclRefExpr(
14526 ParenExpr
*PE
, DependentScopeDeclRefExpr
*DRE
, bool AddrTaken
,
14527 TypeSourceInfo
**RecoveryTSI
) {
14528 ExprResult NewDRE
= getDerived().TransformDependentScopeDeclRefExpr(
14529 DRE
, AddrTaken
, RecoveryTSI
);
14531 // Propagate both errors and recovered types, which return ExprEmpty.
14532 if (!NewDRE
.isUsable())
14535 // We got an expr, wrap it up in parens.
14536 if (!getDerived().AlwaysRebuild() && NewDRE
.get() == DRE
)
14538 return getDerived().RebuildParenExpr(NewDRE
.get(), PE
->getLParen(),
14542 template <typename Derived
>
14543 ExprResult TreeTransform
<Derived
>::TransformDependentScopeDeclRefExpr(
14544 DependentScopeDeclRefExpr
*E
) {
14545 return TransformDependentScopeDeclRefExpr(E
, /*IsAddressOfOperand=*/false,
14549 template <typename Derived
>
14550 ExprResult TreeTransform
<Derived
>::TransformDependentScopeDeclRefExpr(
14551 DependentScopeDeclRefExpr
*E
, bool IsAddressOfOperand
,
14552 TypeSourceInfo
**RecoveryTSI
) {
14553 assert(E
->getQualifierLoc());
14554 NestedNameSpecifierLoc QualifierLoc
=
14555 getDerived().TransformNestedNameSpecifierLoc(E
->getQualifierLoc());
14557 return ExprError();
14558 SourceLocation TemplateKWLoc
= E
->getTemplateKeywordLoc();
14560 // TODO: If this is a conversion-function-id, verify that the
14561 // destination type name (if present) resolves the same way after
14562 // instantiation as it did in the local scope.
14564 DeclarationNameInfo NameInfo
=
14565 getDerived().TransformDeclarationNameInfo(E
->getNameInfo());
14566 if (!NameInfo
.getName())
14567 return ExprError();
14569 if (!E
->hasExplicitTemplateArgs()) {
14570 if (!getDerived().AlwaysRebuild() && QualifierLoc
== E
->getQualifierLoc() &&
14571 // Note: it is sufficient to compare the Name component of NameInfo:
14572 // if name has not changed, DNLoc has not changed either.
14573 NameInfo
.getName() == E
->getDeclName())
14576 return getDerived().RebuildDependentScopeDeclRefExpr(
14577 QualifierLoc
, TemplateKWLoc
, NameInfo
, /*TemplateArgs=*/nullptr,
14578 IsAddressOfOperand
, RecoveryTSI
);
14581 TemplateArgumentListInfo
TransArgs(E
->getLAngleLoc(), E
->getRAngleLoc());
14582 if (getDerived().TransformTemplateArguments(
14583 E
->getTemplateArgs(), E
->getNumTemplateArgs(), TransArgs
))
14584 return ExprError();
14586 return getDerived().RebuildDependentScopeDeclRefExpr(
14587 QualifierLoc
, TemplateKWLoc
, NameInfo
, &TransArgs
, IsAddressOfOperand
,
14591 template<typename Derived
>
14593 TreeTransform
<Derived
>::TransformCXXConstructExpr(CXXConstructExpr
*E
) {
14594 // CXXConstructExprs other than for list-initialization and
14595 // CXXTemporaryObjectExpr are always implicit, so when we have
14596 // a 1-argument construction we just transform that argument.
14597 if (getDerived().AllowSkippingCXXConstructExpr() &&
14598 ((E
->getNumArgs() == 1 ||
14599 (E
->getNumArgs() > 1 && getDerived().DropCallArgument(E
->getArg(1)))) &&
14600 (!getDerived().DropCallArgument(E
->getArg(0))) &&
14601 !E
->isListInitialization()))
14602 return getDerived().TransformInitializer(E
->getArg(0),
14603 /*DirectInit*/ false);
14605 TemporaryBase
Rebase(*this, /*FIXME*/ E
->getBeginLoc(), DeclarationName());
14607 QualType T
= getDerived().TransformType(E
->getType());
14609 return ExprError();
14611 CXXConstructorDecl
*Constructor
= cast_or_null
<CXXConstructorDecl
>(
14612 getDerived().TransformDecl(E
->getBeginLoc(), E
->getConstructor()));
14614 return ExprError();
14616 bool ArgumentChanged
= false;
14617 SmallVector
<Expr
*, 8> Args
;
14619 EnterExpressionEvaluationContext
Context(
14620 getSema(), EnterExpressionEvaluationContext::InitList
,
14621 E
->isListInitialization());
14622 if (getDerived().TransformExprs(E
->getArgs(), E
->getNumArgs(), true, Args
,
14624 return ExprError();
14627 if (!getDerived().AlwaysRebuild() &&
14628 T
== E
->getType() &&
14629 Constructor
== E
->getConstructor() &&
14630 !ArgumentChanged
) {
14631 // Mark the constructor as referenced.
14632 // FIXME: Instantiation-specific
14633 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(), Constructor
);
14637 return getDerived().RebuildCXXConstructExpr(
14638 T
, /*FIXME:*/ E
->getBeginLoc(), Constructor
, E
->isElidable(), Args
,
14639 E
->hadMultipleCandidates(), E
->isListInitialization(),
14640 E
->isStdInitListInitialization(), E
->requiresZeroInitialization(),
14641 E
->getConstructionKind(), E
->getParenOrBraceRange());
14644 template<typename Derived
>
14645 ExprResult TreeTransform
<Derived
>::TransformCXXInheritedCtorInitExpr(
14646 CXXInheritedCtorInitExpr
*E
) {
14647 QualType T
= getDerived().TransformType(E
->getType());
14649 return ExprError();
14651 CXXConstructorDecl
*Constructor
= cast_or_null
<CXXConstructorDecl
>(
14652 getDerived().TransformDecl(E
->getBeginLoc(), E
->getConstructor()));
14654 return ExprError();
14656 if (!getDerived().AlwaysRebuild() &&
14657 T
== E
->getType() &&
14658 Constructor
== E
->getConstructor()) {
14659 // Mark the constructor as referenced.
14660 // FIXME: Instantiation-specific
14661 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(), Constructor
);
14665 return getDerived().RebuildCXXInheritedCtorInitExpr(
14666 T
, E
->getLocation(), Constructor
,
14667 E
->constructsVBase(), E
->inheritedFromVBase());
14670 /// Transform a C++ temporary-binding expression.
14672 /// Since CXXBindTemporaryExpr nodes are implicitly generated, we just
14673 /// transform the subexpression and return that.
14674 template<typename Derived
>
14676 TreeTransform
<Derived
>::TransformCXXBindTemporaryExpr(CXXBindTemporaryExpr
*E
) {
14677 if (auto *Dtor
= E
->getTemporary()->getDestructor())
14678 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(),
14679 const_cast<CXXDestructorDecl
*>(Dtor
));
14680 return getDerived().TransformExpr(E
->getSubExpr());
14683 /// Transform a C++ expression that contains cleanups that should
14684 /// be run after the expression is evaluated.
14686 /// Since ExprWithCleanups nodes are implicitly generated, we
14687 /// just transform the subexpression and return that.
14688 template<typename Derived
>
14690 TreeTransform
<Derived
>::TransformExprWithCleanups(ExprWithCleanups
*E
) {
14691 return getDerived().TransformExpr(E
->getSubExpr());
14694 template<typename Derived
>
14696 TreeTransform
<Derived
>::TransformCXXTemporaryObjectExpr(
14697 CXXTemporaryObjectExpr
*E
) {
14698 TypeSourceInfo
*T
=
14699 getDerived().TransformTypeWithDeducedTST(E
->getTypeSourceInfo());
14701 return ExprError();
14703 CXXConstructorDecl
*Constructor
= cast_or_null
<CXXConstructorDecl
>(
14704 getDerived().TransformDecl(E
->getBeginLoc(), E
->getConstructor()));
14706 return ExprError();
14708 bool ArgumentChanged
= false;
14709 SmallVector
<Expr
*, 8> Args
;
14710 Args
.reserve(E
->getNumArgs());
14712 EnterExpressionEvaluationContext
Context(
14713 getSema(), EnterExpressionEvaluationContext::InitList
,
14714 E
->isListInitialization());
14715 if (TransformExprs(E
->getArgs(), E
->getNumArgs(), true, Args
,
14717 return ExprError();
14719 if (E
->isListInitialization() && !E
->isStdInitListInitialization()) {
14720 ExprResult Res
= RebuildInitList(E
->getBeginLoc(), Args
, E
->getEndLoc());
14721 if (Res
.isInvalid())
14722 return ExprError();
14723 Args
= {Res
.get()};
14727 if (!getDerived().AlwaysRebuild() &&
14728 T
== E
->getTypeSourceInfo() &&
14729 Constructor
== E
->getConstructor() &&
14730 !ArgumentChanged
) {
14731 // FIXME: Instantiation-specific
14732 SemaRef
.MarkFunctionReferenced(E
->getBeginLoc(), Constructor
);
14733 return SemaRef
.MaybeBindToTemporary(E
);
14736 SourceLocation LParenLoc
= T
->getTypeLoc().getEndLoc();
14737 return getDerived().RebuildCXXTemporaryObjectExpr(
14738 T
, LParenLoc
, Args
, E
->getEndLoc(), E
->isListInitialization());
14741 template<typename Derived
>
14743 TreeTransform
<Derived
>::TransformLambdaExpr(LambdaExpr
*E
) {
14744 // Transform any init-capture expressions before entering the scope of the
14745 // lambda body, because they are not semantically within that scope.
14746 typedef std::pair
<ExprResult
, QualType
> InitCaptureInfoTy
;
14747 struct TransformedInitCapture
{
14748 // The location of the ... if the result is retaining a pack expansion.
14749 SourceLocation EllipsisLoc
;
14750 // Zero or more expansions of the init-capture.
14751 SmallVector
<InitCaptureInfoTy
, 4> Expansions
;
14753 SmallVector
<TransformedInitCapture
, 4> InitCaptures
;
14754 InitCaptures
.resize(E
->explicit_capture_end() - E
->explicit_capture_begin());
14755 for (LambdaExpr::capture_iterator C
= E
->capture_begin(),
14756 CEnd
= E
->capture_end();
14758 if (!E
->isInitCapture(C
))
14761 TransformedInitCapture
&Result
= InitCaptures
[C
- E
->capture_begin()];
14762 auto *OldVD
= cast
<VarDecl
>(C
->getCapturedVar());
14764 auto SubstInitCapture
= [&](SourceLocation EllipsisLoc
,
14765 std::optional
<unsigned> NumExpansions
) {
14766 ExprResult NewExprInitResult
= getDerived().TransformInitializer(
14767 OldVD
->getInit(), OldVD
->getInitStyle() == VarDecl::CallInit
);
14769 if (NewExprInitResult
.isInvalid()) {
14770 Result
.Expansions
.push_back(InitCaptureInfoTy(ExprError(), QualType()));
14773 Expr
*NewExprInit
= NewExprInitResult
.get();
14775 QualType NewInitCaptureType
=
14776 getSema().buildLambdaInitCaptureInitialization(
14777 C
->getLocation(), C
->getCaptureKind() == LCK_ByRef
,
14778 EllipsisLoc
, NumExpansions
, OldVD
->getIdentifier(),
14779 cast
<VarDecl
>(C
->getCapturedVar())->getInitStyle() !=
14782 Result
.Expansions
.push_back(
14783 InitCaptureInfoTy(NewExprInit
, NewInitCaptureType
));
14786 // If this is an init-capture pack, consider expanding the pack now.
14787 if (OldVD
->isParameterPack()) {
14788 PackExpansionTypeLoc ExpansionTL
= OldVD
->getTypeSourceInfo()
14790 .castAs
<PackExpansionTypeLoc
>();
14791 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
14792 SemaRef
.collectUnexpandedParameterPacks(OldVD
->getInit(), Unexpanded
);
14794 // Determine whether the set of unexpanded parameter packs can and should
14796 bool Expand
= true;
14797 bool RetainExpansion
= false;
14798 std::optional
<unsigned> OrigNumExpansions
=
14799 ExpansionTL
.getTypePtr()->getNumExpansions();
14800 std::optional
<unsigned> NumExpansions
= OrigNumExpansions
;
14801 if (getDerived().TryExpandParameterPacks(
14802 ExpansionTL
.getEllipsisLoc(),
14803 OldVD
->getInit()->getSourceRange(), Unexpanded
, Expand
,
14804 RetainExpansion
, NumExpansions
))
14805 return ExprError();
14806 assert(!RetainExpansion
&& "Should not need to retain expansion after a "
14807 "capture since it cannot be extended");
14809 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
14810 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
14811 SubstInitCapture(SourceLocation(), std::nullopt
);
14814 SubstInitCapture(ExpansionTL
.getEllipsisLoc(), NumExpansions
);
14815 Result
.EllipsisLoc
= ExpansionTL
.getEllipsisLoc();
14818 SubstInitCapture(SourceLocation(), std::nullopt
);
14822 LambdaScopeInfo
*LSI
= getSema().PushLambdaScope();
14823 Sema::FunctionScopeRAII
FuncScopeCleanup(getSema());
14825 // Create the local class that will describe the lambda.
14827 // FIXME: DependencyKind below is wrong when substituting inside a templated
14828 // context that isn't a DeclContext (such as a variable template), or when
14829 // substituting an unevaluated lambda inside of a function's parameter's type
14830 // - as parameter types are not instantiated from within a function's DC. We
14831 // use evaluation contexts to distinguish the function parameter case.
14832 CXXRecordDecl::LambdaDependencyKind DependencyKind
=
14833 CXXRecordDecl::LDK_Unknown
;
14834 DeclContext
*DC
= getSema().CurContext
;
14835 // A RequiresExprBodyDecl is not interesting for dependencies.
14836 // For the following case,
14838 // template <typename>
14839 // concept C = requires { [] {}; };
14841 // template <class F>
14845 // struct Widget<F> {};
14847 // While we are substituting Widget<F>, the parent of DC would be
14848 // the template specialization itself. Thus, the lambda expression
14849 // will be deemed as dependent even if there are no dependent template
14851 // (A ClassTemplateSpecializationDecl is always a dependent context.)
14852 while (DC
->isRequiresExprBody())
14853 DC
= DC
->getParent();
14854 if ((getSema().isUnevaluatedContext() ||
14855 getSema().isConstantEvaluatedContext()) &&
14856 (DC
->isFileContext() || !DC
->getParent()->isDependentContext()))
14857 DependencyKind
= CXXRecordDecl::LDK_NeverDependent
;
14859 CXXRecordDecl
*OldClass
= E
->getLambdaClass();
14860 CXXRecordDecl
*Class
= getSema().createLambdaClosureType(
14861 E
->getIntroducerRange(), /*Info=*/nullptr, DependencyKind
,
14862 E
->getCaptureDefault());
14863 getDerived().transformedLocalDecl(OldClass
, {Class
});
14865 CXXMethodDecl
*NewCallOperator
=
14866 getSema().CreateLambdaCallOperator(E
->getIntroducerRange(), Class
);
14868 // Enter the scope of the lambda.
14869 getSema().buildLambdaScope(LSI
, NewCallOperator
, E
->getIntroducerRange(),
14870 E
->getCaptureDefault(), E
->getCaptureDefaultLoc(),
14871 E
->hasExplicitParameters(), E
->isMutable());
14873 // Introduce the context of the call operator.
14874 Sema::ContextRAII
SavedContext(getSema(), NewCallOperator
,
14875 /*NewThisContext*/false);
14877 bool Invalid
= false;
14879 // Transform captures.
14880 for (LambdaExpr::capture_iterator C
= E
->capture_begin(),
14881 CEnd
= E
->capture_end();
14883 // When we hit the first implicit capture, tell Sema that we've finished
14884 // the list of explicit captures.
14885 if (C
->isImplicit())
14888 // Capturing 'this' is trivial.
14889 if (C
->capturesThis()) {
14890 // If this is a lambda that is part of a default member initialiser
14891 // and which we're instantiating outside the class that 'this' is
14892 // supposed to refer to, adjust the type of 'this' accordingly.
14894 // Otherwise, leave the type of 'this' as-is.
14895 Sema::CXXThisScopeRAII
ThisScope(
14897 dyn_cast_if_present
<CXXRecordDecl
>(
14898 getSema().getFunctionLevelDeclContext()),
14900 getSema().CheckCXXThisCapture(C
->getLocation(), C
->isExplicit(),
14901 /*BuildAndDiagnose*/ true, nullptr,
14902 C
->getCaptureKind() == LCK_StarThis
);
14905 // Captured expression will be recaptured during captured variables
14907 if (C
->capturesVLAType())
14910 // Rebuild init-captures, including the implied field declaration.
14911 if (E
->isInitCapture(C
)) {
14912 TransformedInitCapture
&NewC
= InitCaptures
[C
- E
->capture_begin()];
14914 auto *OldVD
= cast
<VarDecl
>(C
->getCapturedVar());
14915 llvm::SmallVector
<Decl
*, 4> NewVDs
;
14917 for (InitCaptureInfoTy
&Info
: NewC
.Expansions
) {
14918 ExprResult Init
= Info
.first
;
14919 QualType InitQualType
= Info
.second
;
14920 if (Init
.isInvalid() || InitQualType
.isNull()) {
14924 VarDecl
*NewVD
= getSema().createLambdaInitCaptureVarDecl(
14925 OldVD
->getLocation(), InitQualType
, NewC
.EllipsisLoc
,
14926 OldVD
->getIdentifier(), OldVD
->getInitStyle(), Init
.get(),
14927 getSema().CurContext
);
14932 NewVDs
.push_back(NewVD
);
14933 getSema().addInitCapture(LSI
, NewVD
, C
->getCaptureKind() == LCK_ByRef
);
14934 // Cases we want to tackle:
14935 // ([C(Pack)] {}, ...)
14936 // But rule out cases e.g.
14937 // [...C = Pack()] {}
14938 if (NewC
.EllipsisLoc
.isInvalid())
14939 LSI
->ContainsUnexpandedParameterPack
|=
14940 Init
.get()->containsUnexpandedParameterPack();
14946 getDerived().transformedLocalDecl(OldVD
, NewVDs
);
14950 assert(C
->capturesVariable() && "unexpected kind of lambda capture");
14952 // Determine the capture kind for Sema.
14953 Sema::TryCaptureKind Kind
14954 = C
->isImplicit()? Sema::TryCapture_Implicit
14955 : C
->getCaptureKind() == LCK_ByCopy
14956 ? Sema::TryCapture_ExplicitByVal
14957 : Sema::TryCapture_ExplicitByRef
;
14958 SourceLocation EllipsisLoc
;
14959 if (C
->isPackExpansion()) {
14960 UnexpandedParameterPack
Unexpanded(C
->getCapturedVar(), C
->getLocation());
14961 bool ShouldExpand
= false;
14962 bool RetainExpansion
= false;
14963 std::optional
<unsigned> NumExpansions
;
14964 if (getDerived().TryExpandParameterPacks(C
->getEllipsisLoc(),
14967 ShouldExpand
, RetainExpansion
,
14973 if (ShouldExpand
) {
14974 // The transform has determined that we should perform an expansion;
14975 // transform and capture each of the arguments.
14976 // expansion of the pattern. Do so.
14977 auto *Pack
= cast
<VarDecl
>(C
->getCapturedVar());
14978 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
14979 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
14980 VarDecl
*CapturedVar
14981 = cast_or_null
<VarDecl
>(getDerived().TransformDecl(C
->getLocation(),
14983 if (!CapturedVar
) {
14988 // Capture the transformed variable.
14989 getSema().tryCaptureVariable(CapturedVar
, C
->getLocation(), Kind
);
14992 // FIXME: Retain a pack expansion if RetainExpansion is true.
14997 EllipsisLoc
= C
->getEllipsisLoc();
15000 // Transform the captured variable.
15001 auto *CapturedVar
= cast_or_null
<ValueDecl
>(
15002 getDerived().TransformDecl(C
->getLocation(), C
->getCapturedVar()));
15003 if (!CapturedVar
|| CapturedVar
->isInvalidDecl()) {
15008 // This is not an init-capture; however it contains an unexpanded pack e.g.
15009 // ([Pack] {}(), ...)
15010 if (auto *VD
= dyn_cast
<VarDecl
>(CapturedVar
); VD
&& !C
->isPackExpansion())
15011 LSI
->ContainsUnexpandedParameterPack
|= VD
->isParameterPack();
15013 // Capture the transformed variable.
15014 getSema().tryCaptureVariable(CapturedVar
, C
->getLocation(), Kind
,
15017 getSema().finishLambdaExplicitCaptures(LSI
);
15019 // Transform the template parameters, and add them to the current
15020 // instantiation scope. The null case is handled correctly.
15021 auto TPL
= getDerived().TransformTemplateParameterList(
15022 E
->getTemplateParameterList());
15023 LSI
->GLTemplateParameterList
= TPL
;
15025 getSema().AddTemplateParametersToLambdaCallOperator(NewCallOperator
, Class
,
15027 LSI
->ContainsUnexpandedParameterPack
|=
15028 TPL
->containsUnexpandedParameterPack();
15031 TypeLocBuilder NewCallOpTLBuilder
;
15032 TypeLoc OldCallOpTypeLoc
=
15033 E
->getCallOperator()->getTypeSourceInfo()->getTypeLoc();
15034 QualType NewCallOpType
=
15035 getDerived().TransformType(NewCallOpTLBuilder
, OldCallOpTypeLoc
);
15036 if (NewCallOpType
.isNull())
15037 return ExprError();
15038 LSI
->ContainsUnexpandedParameterPack
|=
15039 NewCallOpType
->containsUnexpandedParameterPack();
15040 TypeSourceInfo
*NewCallOpTSI
=
15041 NewCallOpTLBuilder
.getTypeSourceInfo(getSema().Context
, NewCallOpType
);
15043 // The type may be an AttributedType or some other kind of sugar;
15044 // get the actual underlying FunctionProtoType.
15045 auto FPTL
= NewCallOpTSI
->getTypeLoc().getAsAdjusted
<FunctionProtoTypeLoc
>();
15046 assert(FPTL
&& "Not a FunctionProtoType?");
15048 getSema().CompleteLambdaCallOperator(
15049 NewCallOperator
, E
->getCallOperator()->getLocation(),
15050 E
->getCallOperator()->getInnerLocStart(),
15051 E
->getCallOperator()->getTrailingRequiresClause(), NewCallOpTSI
,
15052 E
->getCallOperator()->getConstexprKind(),
15053 E
->getCallOperator()->getStorageClass(), FPTL
.getParams(),
15054 E
->hasExplicitResultType());
15056 getDerived().transformAttrs(E
->getCallOperator(), NewCallOperator
);
15057 getDerived().transformedLocalDecl(E
->getCallOperator(), {NewCallOperator
});
15060 // Number the lambda for linkage purposes if necessary.
15061 Sema::ContextRAII
ManglingContext(getSema(), Class
->getDeclContext());
15063 std::optional
<CXXRecordDecl::LambdaNumbering
> Numbering
;
15064 if (getDerived().ReplacingOriginal()) {
15065 Numbering
= OldClass
->getLambdaNumbering();
15068 getSema().handleLambdaNumbering(Class
, NewCallOperator
, Numbering
);
15071 // FIXME: Sema's lambda-building mechanism expects us to push an expression
15072 // evaluation context even if we're not transforming the function body.
15073 getSema().PushExpressionEvaluationContext(
15074 E
->getCallOperator()->isConsteval() ?
15075 Sema::ExpressionEvaluationContext::ImmediateFunctionContext
:
15076 Sema::ExpressionEvaluationContext::PotentiallyEvaluated
);
15077 getSema().currentEvaluationContext().InImmediateEscalatingFunctionContext
=
15078 getSema().getLangOpts().CPlusPlus20
&&
15079 E
->getCallOperator()->isImmediateEscalating();
15081 Sema::CodeSynthesisContext C
;
15082 C
.Kind
= clang::Sema::CodeSynthesisContext::LambdaExpressionSubstitution
;
15083 C
.PointOfInstantiation
= E
->getBody()->getBeginLoc();
15084 getSema().pushCodeSynthesisContext(C
);
15086 // Instantiate the body of the lambda expression.
15088 Invalid
? StmtError() : getDerived().TransformLambdaBody(E
, E
->getBody());
15090 getSema().popCodeSynthesisContext();
15092 // ActOnLambda* will pop the function scope for us.
15093 FuncScopeCleanup
.disable();
15095 if (Body
.isInvalid()) {
15096 SavedContext
.pop();
15097 getSema().ActOnLambdaError(E
->getBeginLoc(), /*CurScope=*/nullptr,
15098 /*IsInstantiation=*/true);
15099 return ExprError();
15102 // Copy the LSI before ActOnFinishFunctionBody removes it.
15103 // FIXME: This is dumb. Store the lambda information somewhere that outlives
15104 // the call operator.
15105 auto LSICopy
= *LSI
;
15106 getSema().ActOnFinishFunctionBody(NewCallOperator
, Body
.get(),
15107 /*IsInstantiation*/ true);
15108 SavedContext
.pop();
15110 // Recompute the dependency of the lambda so that we can defer the lambda call
15111 // construction until after we have all the necessary template arguments. For
15114 // template <class> struct S {
15115 // template <class U>
15116 // using Type = decltype([](U){}(42.0));
15119 // using T = S<int>::Type<float>;
15123 // We would end up here from instantiating S<int> when ensuring its
15124 // completeness. That would transform the lambda call expression regardless of
15125 // the absence of the corresponding argument for U.
15127 // Going ahead with unsubstituted type U makes things worse: we would soon
15128 // compare the argument type (which is float) against the parameter U
15129 // somewhere in Sema::BuildCallExpr. Then we would quickly run into a bogus
15130 // error suggesting unmatched types 'U' and 'float'!
15132 // That said, everything will be fine if we defer that semantic checking.
15133 // Fortunately, we have such a mechanism that bypasses it if the CallExpr is
15134 // dependent. Since the CallExpr's dependency boils down to the lambda's
15135 // dependency in this case, we can harness that by recomputing the dependency
15136 // from the instantiation arguments.
15138 // FIXME: Creating the type of a lambda requires us to have a dependency
15139 // value, which happens before its substitution. We update its dependency
15140 // *after* the substitution in case we can't decide the dependency
15141 // so early, e.g. because we want to see if any of the *substituted*
15142 // parameters are dependent.
15143 DependencyKind
= getDerived().ComputeLambdaDependency(&LSICopy
);
15144 Class
->setLambdaDependencyKind(DependencyKind
);
15145 // Clean up the type cache created previously. Then, we re-create a type for
15146 // such Decl with the new DependencyKind.
15147 Class
->setTypeForDecl(nullptr);
15148 getSema().Context
.getTypeDeclType(Class
);
15150 return getDerived().RebuildLambdaExpr(E
->getBeginLoc(),
15151 Body
.get()->getEndLoc(), &LSICopy
);
15154 template<typename Derived
>
15156 TreeTransform
<Derived
>::TransformLambdaBody(LambdaExpr
*E
, Stmt
*S
) {
15157 return TransformStmt(S
);
15160 template<typename Derived
>
15162 TreeTransform
<Derived
>::SkipLambdaBody(LambdaExpr
*E
, Stmt
*S
) {
15163 // Transform captures.
15164 for (LambdaExpr::capture_iterator C
= E
->capture_begin(),
15165 CEnd
= E
->capture_end();
15167 // When we hit the first implicit capture, tell Sema that we've finished
15168 // the list of explicit captures.
15169 if (!C
->isImplicit())
15172 // Capturing 'this' is trivial.
15173 if (C
->capturesThis()) {
15174 getSema().CheckCXXThisCapture(C
->getLocation(), C
->isExplicit(),
15175 /*BuildAndDiagnose*/ true, nullptr,
15176 C
->getCaptureKind() == LCK_StarThis
);
15179 // Captured expression will be recaptured during captured variables
15181 if (C
->capturesVLAType())
15184 assert(C
->capturesVariable() && "unexpected kind of lambda capture");
15185 assert(!E
->isInitCapture(C
) && "implicit init-capture?");
15187 // Transform the captured variable.
15188 VarDecl
*CapturedVar
= cast_or_null
<VarDecl
>(
15189 getDerived().TransformDecl(C
->getLocation(), C
->getCapturedVar()));
15190 if (!CapturedVar
|| CapturedVar
->isInvalidDecl())
15191 return StmtError();
15193 // Capture the transformed variable.
15194 getSema().tryCaptureVariable(CapturedVar
, C
->getLocation());
15200 template<typename Derived
>
15202 TreeTransform
<Derived
>::TransformCXXUnresolvedConstructExpr(
15203 CXXUnresolvedConstructExpr
*E
) {
15204 TypeSourceInfo
*T
=
15205 getDerived().TransformTypeWithDeducedTST(E
->getTypeSourceInfo());
15207 return ExprError();
15209 bool ArgumentChanged
= false;
15210 SmallVector
<Expr
*, 8> Args
;
15211 Args
.reserve(E
->getNumArgs());
15213 EnterExpressionEvaluationContext
Context(
15214 getSema(), EnterExpressionEvaluationContext::InitList
,
15215 E
->isListInitialization());
15216 if (getDerived().TransformExprs(E
->arg_begin(), E
->getNumArgs(), true, Args
,
15218 return ExprError();
15221 if (!getDerived().AlwaysRebuild() &&
15222 T
== E
->getTypeSourceInfo() &&
15226 // FIXME: we're faking the locations of the commas
15227 return getDerived().RebuildCXXUnresolvedConstructExpr(
15228 T
, E
->getLParenLoc(), Args
, E
->getRParenLoc(), E
->isListInitialization());
15231 template<typename Derived
>
15233 TreeTransform
<Derived
>::TransformCXXDependentScopeMemberExpr(
15234 CXXDependentScopeMemberExpr
*E
) {
15235 // Transform the base of the expression.
15236 ExprResult
Base((Expr
*) nullptr);
15239 QualType ObjectType
;
15240 if (!E
->isImplicitAccess()) {
15241 OldBase
= E
->getBase();
15242 Base
= getDerived().TransformExpr(OldBase
);
15243 if (Base
.isInvalid())
15244 return ExprError();
15246 // Start the member reference and compute the object's type.
15247 ParsedType ObjectTy
;
15248 bool MayBePseudoDestructor
= false;
15249 Base
= SemaRef
.ActOnStartCXXMemberReference(nullptr, Base
.get(),
15250 E
->getOperatorLoc(),
15251 E
->isArrow()? tok::arrow
: tok::period
,
15253 MayBePseudoDestructor
);
15254 if (Base
.isInvalid())
15255 return ExprError();
15257 ObjectType
= ObjectTy
.get();
15258 BaseType
= ((Expr
*) Base
.get())->getType();
15261 BaseType
= getDerived().TransformType(E
->getBaseType());
15262 ObjectType
= BaseType
->castAs
<PointerType
>()->getPointeeType();
15265 // Transform the first part of the nested-name-specifier that qualifies
15266 // the member name.
15267 NamedDecl
*FirstQualifierInScope
15268 = getDerived().TransformFirstQualifierInScope(
15269 E
->getFirstQualifierFoundInScope(),
15270 E
->getQualifierLoc().getBeginLoc());
15272 NestedNameSpecifierLoc QualifierLoc
;
15273 if (E
->getQualifier()) {
15275 = getDerived().TransformNestedNameSpecifierLoc(E
->getQualifierLoc(),
15277 FirstQualifierInScope
);
15279 return ExprError();
15282 SourceLocation TemplateKWLoc
= E
->getTemplateKeywordLoc();
15284 // TODO: If this is a conversion-function-id, verify that the
15285 // destination type name (if present) resolves the same way after
15286 // instantiation as it did in the local scope.
15288 DeclarationNameInfo NameInfo
15289 = getDerived().TransformDeclarationNameInfo(E
->getMemberNameInfo());
15290 if (!NameInfo
.getName())
15291 return ExprError();
15293 if (!E
->hasExplicitTemplateArgs()) {
15294 // This is a reference to a member without an explicitly-specified
15295 // template argument list. Optimize for this common case.
15296 if (!getDerived().AlwaysRebuild() &&
15297 Base
.get() == OldBase
&&
15298 BaseType
== E
->getBaseType() &&
15299 QualifierLoc
== E
->getQualifierLoc() &&
15300 NameInfo
.getName() == E
->getMember() &&
15301 FirstQualifierInScope
== E
->getFirstQualifierFoundInScope())
15304 return getDerived().RebuildCXXDependentScopeMemberExpr(Base
.get(),
15307 E
->getOperatorLoc(),
15310 FirstQualifierInScope
,
15312 /*TemplateArgs*/nullptr);
15315 TemplateArgumentListInfo
TransArgs(E
->getLAngleLoc(), E
->getRAngleLoc());
15316 if (getDerived().TransformTemplateArguments(E
->getTemplateArgs(),
15317 E
->getNumTemplateArgs(),
15319 return ExprError();
15321 return getDerived().RebuildCXXDependentScopeMemberExpr(Base
.get(),
15324 E
->getOperatorLoc(),
15327 FirstQualifierInScope
,
15332 template <typename Derived
>
15333 ExprResult TreeTransform
<Derived
>::TransformUnresolvedMemberExpr(
15334 UnresolvedMemberExpr
*Old
) {
15335 // Transform the base of the expression.
15336 ExprResult
Base((Expr
*)nullptr);
15338 if (!Old
->isImplicitAccess()) {
15339 Base
= getDerived().TransformExpr(Old
->getBase());
15340 if (Base
.isInvalid())
15341 return ExprError();
15343 getSema().PerformMemberExprBaseConversion(Base
.get(), Old
->isArrow());
15344 if (Base
.isInvalid())
15345 return ExprError();
15346 BaseType
= Base
.get()->getType();
15348 BaseType
= getDerived().TransformType(Old
->getBaseType());
15351 NestedNameSpecifierLoc QualifierLoc
;
15352 if (Old
->getQualifierLoc()) {
15354 getDerived().TransformNestedNameSpecifierLoc(Old
->getQualifierLoc());
15356 return ExprError();
15359 SourceLocation TemplateKWLoc
= Old
->getTemplateKeywordLoc();
15361 LookupResult
R(SemaRef
, Old
->getMemberNameInfo(), Sema::LookupOrdinaryName
);
15363 // Transform the declaration set.
15364 if (TransformOverloadExprDecls(Old
, /*RequiresADL*/ false, R
))
15365 return ExprError();
15367 // Determine the naming class.
15368 if (Old
->getNamingClass()) {
15369 CXXRecordDecl
*NamingClass
= cast_or_null
<CXXRecordDecl
>(
15370 getDerived().TransformDecl(Old
->getMemberLoc(), Old
->getNamingClass()));
15372 return ExprError();
15374 R
.setNamingClass(NamingClass
);
15377 TemplateArgumentListInfo TransArgs
;
15378 if (Old
->hasExplicitTemplateArgs()) {
15379 TransArgs
.setLAngleLoc(Old
->getLAngleLoc());
15380 TransArgs
.setRAngleLoc(Old
->getRAngleLoc());
15381 if (getDerived().TransformTemplateArguments(
15382 Old
->getTemplateArgs(), Old
->getNumTemplateArgs(), TransArgs
))
15383 return ExprError();
15386 // FIXME: to do this check properly, we will need to preserve the
15387 // first-qualifier-in-scope here, just in case we had a dependent
15388 // base (and therefore couldn't do the check) and a
15389 // nested-name-qualifier (and therefore could do the lookup).
15390 NamedDecl
*FirstQualifierInScope
= nullptr;
15392 return getDerived().RebuildUnresolvedMemberExpr(
15393 Base
.get(), BaseType
, Old
->getOperatorLoc(), Old
->isArrow(), QualifierLoc
,
15394 TemplateKWLoc
, FirstQualifierInScope
, R
,
15395 (Old
->hasExplicitTemplateArgs() ? &TransArgs
: nullptr));
15398 template<typename Derived
>
15400 TreeTransform
<Derived
>::TransformCXXNoexceptExpr(CXXNoexceptExpr
*E
) {
15401 EnterExpressionEvaluationContext
Unevaluated(
15402 SemaRef
, Sema::ExpressionEvaluationContext::Unevaluated
);
15403 ExprResult SubExpr
= getDerived().TransformExpr(E
->getOperand());
15404 if (SubExpr
.isInvalid())
15405 return ExprError();
15407 if (!getDerived().AlwaysRebuild() && SubExpr
.get() == E
->getOperand())
15410 return getDerived().RebuildCXXNoexceptExpr(E
->getSourceRange(),SubExpr
.get());
15413 template<typename Derived
>
15415 TreeTransform
<Derived
>::TransformPackExpansionExpr(PackExpansionExpr
*E
) {
15416 ExprResult Pattern
= getDerived().TransformExpr(E
->getPattern());
15417 if (Pattern
.isInvalid())
15418 return ExprError();
15420 if (!getDerived().AlwaysRebuild() && Pattern
.get() == E
->getPattern())
15423 return getDerived().RebuildPackExpansion(Pattern
.get(), E
->getEllipsisLoc(),
15424 E
->getNumExpansions());
15427 template<typename Derived
>
15429 TreeTransform
<Derived
>::TransformSizeOfPackExpr(SizeOfPackExpr
*E
) {
15430 // If E is not value-dependent, then nothing will change when we transform it.
15431 // Note: This is an instantiation-centric view.
15432 if (!E
->isValueDependent())
15435 EnterExpressionEvaluationContext
Unevaluated(
15436 getSema(), Sema::ExpressionEvaluationContext::Unevaluated
);
15438 ArrayRef
<TemplateArgument
> PackArgs
;
15439 TemplateArgument ArgStorage
;
15441 // Find the argument list to transform.
15442 if (E
->isPartiallySubstituted()) {
15443 PackArgs
= E
->getPartialArguments();
15444 } else if (E
->isValueDependent()) {
15445 UnexpandedParameterPack
Unexpanded(E
->getPack(), E
->getPackLoc());
15446 bool ShouldExpand
= false;
15447 bool RetainExpansion
= false;
15448 std::optional
<unsigned> NumExpansions
;
15449 if (getDerived().TryExpandParameterPacks(E
->getOperatorLoc(), E
->getPackLoc(),
15451 ShouldExpand
, RetainExpansion
,
15453 return ExprError();
15455 // If we need to expand the pack, build a template argument from it and
15457 if (ShouldExpand
) {
15458 auto *Pack
= E
->getPack();
15459 if (auto *TTPD
= dyn_cast
<TemplateTypeParmDecl
>(Pack
)) {
15460 ArgStorage
= getSema().Context
.getPackExpansionType(
15461 getSema().Context
.getTypeDeclType(TTPD
), std::nullopt
);
15462 } else if (auto *TTPD
= dyn_cast
<TemplateTemplateParmDecl
>(Pack
)) {
15463 ArgStorage
= TemplateArgument(TemplateName(TTPD
), std::nullopt
);
15465 auto *VD
= cast
<ValueDecl
>(Pack
);
15466 ExprResult DRE
= getSema().BuildDeclRefExpr(
15467 VD
, VD
->getType().getNonLValueExprType(getSema().Context
),
15468 VD
->getType()->isReferenceType() ? VK_LValue
: VK_PRValue
,
15470 if (DRE
.isInvalid())
15471 return ExprError();
15472 ArgStorage
= new (getSema().Context
)
15473 PackExpansionExpr(getSema().Context
.DependentTy
, DRE
.get(),
15474 E
->getPackLoc(), std::nullopt
);
15476 PackArgs
= ArgStorage
;
15480 // If we're not expanding the pack, just transform the decl.
15481 if (!PackArgs
.size()) {
15482 auto *Pack
= cast_or_null
<NamedDecl
>(
15483 getDerived().TransformDecl(E
->getPackLoc(), E
->getPack()));
15485 return ExprError();
15486 return getDerived().RebuildSizeOfPackExpr(
15487 E
->getOperatorLoc(), Pack
, E
->getPackLoc(), E
->getRParenLoc(),
15491 // Try to compute the result without performing a partial substitution.
15492 std::optional
<unsigned> Result
= 0;
15493 for (const TemplateArgument
&Arg
: PackArgs
) {
15494 if (!Arg
.isPackExpansion()) {
15495 Result
= *Result
+ 1;
15499 TemplateArgumentLoc ArgLoc
;
15500 InventTemplateArgumentLoc(Arg
, ArgLoc
);
15502 // Find the pattern of the pack expansion.
15503 SourceLocation Ellipsis
;
15504 std::optional
<unsigned> OrigNumExpansions
;
15505 TemplateArgumentLoc Pattern
=
15506 getSema().getTemplateArgumentPackExpansionPattern(ArgLoc
, Ellipsis
,
15507 OrigNumExpansions
);
15509 // Substitute under the pack expansion. Do not expand the pack (yet).
15510 TemplateArgumentLoc OutPattern
;
15511 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
15512 if (getDerived().TransformTemplateArgument(Pattern
, OutPattern
,
15516 // See if we can determine the number of arguments from the result.
15517 std::optional
<unsigned> NumExpansions
=
15518 getSema().getFullyPackExpandedSize(OutPattern
.getArgument());
15519 if (!NumExpansions
) {
15520 // No: we must be in an alias template expansion, and we're going to need
15521 // to actually expand the packs.
15522 Result
= std::nullopt
;
15526 Result
= *Result
+ *NumExpansions
;
15529 // Common case: we could determine the number of expansions without
15532 return getDerived().RebuildSizeOfPackExpr(E
->getOperatorLoc(), E
->getPack(),
15534 E
->getRParenLoc(), *Result
, {});
15536 TemplateArgumentListInfo
TransformedPackArgs(E
->getPackLoc(),
15539 TemporaryBase
Rebase(*this, E
->getPackLoc(), getBaseEntity());
15540 typedef TemplateArgumentLocInventIterator
<
15541 Derived
, const TemplateArgument
*> PackLocIterator
;
15542 if (TransformTemplateArguments(PackLocIterator(*this, PackArgs
.begin()),
15543 PackLocIterator(*this, PackArgs
.end()),
15544 TransformedPackArgs
, /*Uneval*/true))
15545 return ExprError();
15548 // Check whether we managed to fully-expand the pack.
15549 // FIXME: Is it possible for us to do so and not hit the early exit path?
15550 SmallVector
<TemplateArgument
, 8> Args
;
15551 bool PartialSubstitution
= false;
15552 for (auto &Loc
: TransformedPackArgs
.arguments()) {
15553 Args
.push_back(Loc
.getArgument());
15554 if (Loc
.getArgument().isPackExpansion())
15555 PartialSubstitution
= true;
15558 if (PartialSubstitution
)
15559 return getDerived().RebuildSizeOfPackExpr(
15560 E
->getOperatorLoc(), E
->getPack(), E
->getPackLoc(), E
->getRParenLoc(),
15561 std::nullopt
, Args
);
15563 return getDerived().RebuildSizeOfPackExpr(E
->getOperatorLoc(), E
->getPack(),
15564 E
->getPackLoc(), E
->getRParenLoc(),
15568 template <typename Derived
>
15570 TreeTransform
<Derived
>::TransformPackIndexingExpr(PackIndexingExpr
*E
) {
15571 if (!E
->isValueDependent())
15574 // Transform the index
15575 ExprResult IndexExpr
;
15577 EnterExpressionEvaluationContext
ConstantContext(
15578 SemaRef
, Sema::ExpressionEvaluationContext::ConstantEvaluated
);
15579 IndexExpr
= getDerived().TransformExpr(E
->getIndexExpr());
15580 if (IndexExpr
.isInvalid())
15581 return ExprError();
15584 SmallVector
<Expr
*, 5> ExpandedExprs
;
15585 bool FullySubstituted
= true;
15586 if (!E
->expandsToEmptyPack() && E
->getExpressions().empty()) {
15587 Expr
*Pattern
= E
->getPackIdExpression();
15588 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
15589 getSema().collectUnexpandedParameterPacks(E
->getPackIdExpression(),
15591 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
15593 // Determine whether the set of unexpanded parameter packs can and should
15595 bool ShouldExpand
= true;
15596 bool RetainExpansion
= false;
15597 std::optional
<unsigned> OrigNumExpansions
;
15598 std::optional
<unsigned> NumExpansions
= OrigNumExpansions
;
15599 if (getDerived().TryExpandParameterPacks(
15600 E
->getEllipsisLoc(), Pattern
->getSourceRange(), Unexpanded
,
15601 ShouldExpand
, RetainExpansion
, NumExpansions
))
15603 if (!ShouldExpand
) {
15604 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
15605 ExprResult Pack
= getDerived().TransformExpr(Pattern
);
15606 if (Pack
.isInvalid())
15607 return ExprError();
15608 return getDerived().RebuildPackIndexingExpr(
15609 E
->getEllipsisLoc(), E
->getRSquareLoc(), Pack
.get(), IndexExpr
.get(),
15610 {}, /*FullySubstituted=*/false);
15612 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
15613 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
15614 ExprResult Out
= getDerived().TransformExpr(Pattern
);
15615 if (Out
.isInvalid())
15617 if (Out
.get()->containsUnexpandedParameterPack()) {
15618 Out
= getDerived().RebuildPackExpansion(Out
.get(), E
->getEllipsisLoc(),
15619 OrigNumExpansions
);
15620 if (Out
.isInvalid())
15622 FullySubstituted
= false;
15624 ExpandedExprs
.push_back(Out
.get());
15626 // If we're supposed to retain a pack expansion, do so by temporarily
15627 // forgetting the partially-substituted parameter pack.
15628 if (RetainExpansion
) {
15629 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
15631 ExprResult Out
= getDerived().TransformExpr(Pattern
);
15632 if (Out
.isInvalid())
15635 Out
= getDerived().RebuildPackExpansion(Out
.get(), E
->getEllipsisLoc(),
15636 OrigNumExpansions
);
15637 if (Out
.isInvalid())
15639 FullySubstituted
= false;
15640 ExpandedExprs
.push_back(Out
.get());
15642 } else if (!E
->expandsToEmptyPack()) {
15643 if (getDerived().TransformExprs(E
->getExpressions().data(),
15644 E
->getExpressions().size(), false,
15646 return ExprError();
15649 return getDerived().RebuildPackIndexingExpr(
15650 E
->getEllipsisLoc(), E
->getRSquareLoc(), E
->getPackIdExpression(),
15651 IndexExpr
.get(), ExpandedExprs
, FullySubstituted
);
15654 template<typename Derived
>
15656 TreeTransform
<Derived
>::TransformSubstNonTypeTemplateParmPackExpr(
15657 SubstNonTypeTemplateParmPackExpr
*E
) {
15658 // Default behavior is to do nothing with this transformation.
15662 template<typename Derived
>
15664 TreeTransform
<Derived
>::TransformSubstNonTypeTemplateParmExpr(
15665 SubstNonTypeTemplateParmExpr
*E
) {
15666 // Default behavior is to do nothing with this transformation.
15670 template<typename Derived
>
15672 TreeTransform
<Derived
>::TransformFunctionParmPackExpr(FunctionParmPackExpr
*E
) {
15673 // Default behavior is to do nothing with this transformation.
15677 template<typename Derived
>
15679 TreeTransform
<Derived
>::TransformMaterializeTemporaryExpr(
15680 MaterializeTemporaryExpr
*E
) {
15681 return getDerived().TransformExpr(E
->getSubExpr());
15684 template<typename Derived
>
15686 TreeTransform
<Derived
>::TransformCXXFoldExpr(CXXFoldExpr
*E
) {
15687 UnresolvedLookupExpr
*Callee
= nullptr;
15688 if (Expr
*OldCallee
= E
->getCallee()) {
15689 ExprResult CalleeResult
= getDerived().TransformExpr(OldCallee
);
15690 if (CalleeResult
.isInvalid())
15691 return ExprError();
15692 Callee
= cast
<UnresolvedLookupExpr
>(CalleeResult
.get());
15695 Expr
*Pattern
= E
->getPattern();
15697 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
15698 getSema().collectUnexpandedParameterPacks(Pattern
, Unexpanded
);
15699 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
15701 // Determine whether the set of unexpanded parameter packs can and should
15703 bool Expand
= true;
15704 bool RetainExpansion
= false;
15705 std::optional
<unsigned> OrigNumExpansions
= E
->getNumExpansions(),
15706 NumExpansions
= OrigNumExpansions
;
15707 if (getDerived().TryExpandParameterPacks(E
->getEllipsisLoc(),
15708 Pattern
->getSourceRange(),
15710 Expand
, RetainExpansion
,
15715 // Do not expand any packs here, just transform and rebuild a fold
15717 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
15720 E
->getLHS() ? getDerived().TransformExpr(E
->getLHS()) : ExprResult();
15721 if (LHS
.isInvalid())
15725 E
->getRHS() ? getDerived().TransformExpr(E
->getRHS()) : ExprResult();
15726 if (RHS
.isInvalid())
15729 if (!getDerived().AlwaysRebuild() &&
15730 LHS
.get() == E
->getLHS() && RHS
.get() == E
->getRHS())
15733 return getDerived().RebuildCXXFoldExpr(
15734 Callee
, E
->getBeginLoc(), LHS
.get(), E
->getOperator(),
15735 E
->getEllipsisLoc(), RHS
.get(), E
->getEndLoc(), NumExpansions
);
15738 // Formally a fold expression expands to nested parenthesized expressions.
15739 // Enforce this limit to avoid creating trees so deep we can't safely traverse
15741 if (NumExpansions
&& SemaRef
.getLangOpts().BracketDepth
< NumExpansions
) {
15742 SemaRef
.Diag(E
->getEllipsisLoc(),
15743 clang::diag::err_fold_expression_limit_exceeded
)
15744 << *NumExpansions
<< SemaRef
.getLangOpts().BracketDepth
15745 << E
->getSourceRange();
15746 SemaRef
.Diag(E
->getEllipsisLoc(), diag::note_bracket_depth
);
15747 return ExprError();
15750 // The transform has determined that we should perform an elementwise
15751 // expansion of the pattern. Do so.
15752 ExprResult Result
= getDerived().TransformExpr(E
->getInit());
15753 if (Result
.isInvalid())
15755 bool LeftFold
= E
->isLeftFold();
15757 // If we're retaining an expansion for a right fold, it is the innermost
15758 // component and takes the init (if any).
15759 if (!LeftFold
&& RetainExpansion
) {
15760 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
15762 ExprResult Out
= getDerived().TransformExpr(Pattern
);
15763 if (Out
.isInvalid())
15766 Result
= getDerived().RebuildCXXFoldExpr(
15767 Callee
, E
->getBeginLoc(), Out
.get(), E
->getOperator(),
15768 E
->getEllipsisLoc(), Result
.get(), E
->getEndLoc(), OrigNumExpansions
);
15769 if (Result
.isInvalid())
15773 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
15774 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(
15775 getSema(), LeftFold
? I
: *NumExpansions
- I
- 1);
15776 ExprResult Out
= getDerived().TransformExpr(Pattern
);
15777 if (Out
.isInvalid())
15780 if (Out
.get()->containsUnexpandedParameterPack()) {
15781 // We still have a pack; retain a pack expansion for this slice.
15782 Result
= getDerived().RebuildCXXFoldExpr(
15783 Callee
, E
->getBeginLoc(), LeftFold
? Result
.get() : Out
.get(),
15784 E
->getOperator(), E
->getEllipsisLoc(),
15785 LeftFold
? Out
.get() : Result
.get(), E
->getEndLoc(),
15786 OrigNumExpansions
);
15787 } else if (Result
.isUsable()) {
15788 // We've got down to a single element; build a binary operator.
15789 Expr
*LHS
= LeftFold
? Result
.get() : Out
.get();
15790 Expr
*RHS
= LeftFold
? Out
.get() : Result
.get();
15792 UnresolvedSet
<16> Functions
;
15793 Functions
.append(Callee
->decls_begin(), Callee
->decls_end());
15794 Result
= getDerived().RebuildCXXOperatorCallExpr(
15795 BinaryOperator::getOverloadedOperator(E
->getOperator()),
15796 E
->getEllipsisLoc(), Callee
->getBeginLoc(), Callee
->requiresADL(),
15797 Functions
, LHS
, RHS
);
15799 Result
= getDerived().RebuildBinaryOperator(E
->getEllipsisLoc(),
15800 E
->getOperator(), LHS
, RHS
);
15805 if (Result
.isInvalid())
15809 // If we're retaining an expansion for a left fold, it is the outermost
15810 // component and takes the complete expansion so far as its init (if any).
15811 if (LeftFold
&& RetainExpansion
) {
15812 ForgetPartiallySubstitutedPackRAII
Forget(getDerived());
15814 ExprResult Out
= getDerived().TransformExpr(Pattern
);
15815 if (Out
.isInvalid())
15818 Result
= getDerived().RebuildCXXFoldExpr(
15819 Callee
, E
->getBeginLoc(), Result
.get(), E
->getOperator(),
15820 E
->getEllipsisLoc(), Out
.get(), E
->getEndLoc(), OrigNumExpansions
);
15821 if (Result
.isInvalid())
15825 if (ParenExpr
*PE
= dyn_cast_or_null
<ParenExpr
>(Result
.get()))
15826 PE
->setIsProducedByFoldExpansion();
15828 // If we had no init and an empty pack, and we're not retaining an expansion,
15829 // then produce a fallback value or error.
15830 if (Result
.isUnset())
15831 return getDerived().RebuildEmptyCXXFoldExpr(E
->getEllipsisLoc(),
15836 template <typename Derived
>
15838 TreeTransform
<Derived
>::TransformCXXParenListInitExpr(CXXParenListInitExpr
*E
) {
15839 SmallVector
<Expr
*, 4> TransformedInits
;
15840 ArrayRef
<Expr
*> InitExprs
= E
->getInitExprs();
15841 if (TransformExprs(InitExprs
.data(), InitExprs
.size(), true,
15843 return ExprError();
15845 return getDerived().RebuildParenListExpr(E
->getBeginLoc(), TransformedInits
,
15849 template<typename Derived
>
15851 TreeTransform
<Derived
>::TransformCXXStdInitializerListExpr(
15852 CXXStdInitializerListExpr
*E
) {
15853 return getDerived().TransformExpr(E
->getSubExpr());
15856 template<typename Derived
>
15858 TreeTransform
<Derived
>::TransformObjCStringLiteral(ObjCStringLiteral
*E
) {
15859 return SemaRef
.MaybeBindToTemporary(E
);
15862 template<typename Derived
>
15864 TreeTransform
<Derived
>::TransformObjCBoolLiteralExpr(ObjCBoolLiteralExpr
*E
) {
15868 template<typename Derived
>
15870 TreeTransform
<Derived
>::TransformObjCBoxedExpr(ObjCBoxedExpr
*E
) {
15871 ExprResult SubExpr
= getDerived().TransformExpr(E
->getSubExpr());
15872 if (SubExpr
.isInvalid())
15873 return ExprError();
15875 if (!getDerived().AlwaysRebuild() &&
15876 SubExpr
.get() == E
->getSubExpr())
15879 return getDerived().RebuildObjCBoxedExpr(E
->getSourceRange(), SubExpr
.get());
15882 template<typename Derived
>
15884 TreeTransform
<Derived
>::TransformObjCArrayLiteral(ObjCArrayLiteral
*E
) {
15885 // Transform each of the elements.
15886 SmallVector
<Expr
*, 8> Elements
;
15887 bool ArgChanged
= false;
15888 if (getDerived().TransformExprs(E
->getElements(), E
->getNumElements(),
15889 /*IsCall=*/false, Elements
, &ArgChanged
))
15890 return ExprError();
15892 if (!getDerived().AlwaysRebuild() && !ArgChanged
)
15893 return SemaRef
.MaybeBindToTemporary(E
);
15895 return getDerived().RebuildObjCArrayLiteral(E
->getSourceRange(),
15900 template<typename Derived
>
15902 TreeTransform
<Derived
>::TransformObjCDictionaryLiteral(
15903 ObjCDictionaryLiteral
*E
) {
15904 // Transform each of the elements.
15905 SmallVector
<ObjCDictionaryElement
, 8> Elements
;
15906 bool ArgChanged
= false;
15907 for (unsigned I
= 0, N
= E
->getNumElements(); I
!= N
; ++I
) {
15908 ObjCDictionaryElement OrigElement
= E
->getKeyValueElement(I
);
15910 if (OrigElement
.isPackExpansion()) {
15911 // This key/value element is a pack expansion.
15912 SmallVector
<UnexpandedParameterPack
, 2> Unexpanded
;
15913 getSema().collectUnexpandedParameterPacks(OrigElement
.Key
, Unexpanded
);
15914 getSema().collectUnexpandedParameterPacks(OrigElement
.Value
, Unexpanded
);
15915 assert(!Unexpanded
.empty() && "Pack expansion without parameter packs?");
15917 // Determine whether the set of unexpanded parameter packs can
15918 // and should be expanded.
15919 bool Expand
= true;
15920 bool RetainExpansion
= false;
15921 std::optional
<unsigned> OrigNumExpansions
= OrigElement
.NumExpansions
;
15922 std::optional
<unsigned> NumExpansions
= OrigNumExpansions
;
15923 SourceRange
PatternRange(OrigElement
.Key
->getBeginLoc(),
15924 OrigElement
.Value
->getEndLoc());
15925 if (getDerived().TryExpandParameterPacks(OrigElement
.EllipsisLoc
,
15926 PatternRange
, Unexpanded
, Expand
,
15927 RetainExpansion
, NumExpansions
))
15928 return ExprError();
15931 // The transform has determined that we should perform a simple
15932 // transformation on the pack expansion, producing another pack
15934 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), -1);
15935 ExprResult Key
= getDerived().TransformExpr(OrigElement
.Key
);
15936 if (Key
.isInvalid())
15937 return ExprError();
15939 if (Key
.get() != OrigElement
.Key
)
15942 ExprResult Value
= getDerived().TransformExpr(OrigElement
.Value
);
15943 if (Value
.isInvalid())
15944 return ExprError();
15946 if (Value
.get() != OrigElement
.Value
)
15949 ObjCDictionaryElement Expansion
= {
15950 Key
.get(), Value
.get(), OrigElement
.EllipsisLoc
, NumExpansions
15952 Elements
.push_back(Expansion
);
15956 // Record right away that the argument was changed. This needs
15957 // to happen even if the array expands to nothing.
15960 // The transform has determined that we should perform an elementwise
15961 // expansion of the pattern. Do so.
15962 for (unsigned I
= 0; I
!= *NumExpansions
; ++I
) {
15963 Sema::ArgumentPackSubstitutionIndexRAII
SubstIndex(getSema(), I
);
15964 ExprResult Key
= getDerived().TransformExpr(OrigElement
.Key
);
15965 if (Key
.isInvalid())
15966 return ExprError();
15968 ExprResult Value
= getDerived().TransformExpr(OrigElement
.Value
);
15969 if (Value
.isInvalid())
15970 return ExprError();
15972 ObjCDictionaryElement Element
= {
15973 Key
.get(), Value
.get(), SourceLocation(), NumExpansions
15976 // If any unexpanded parameter packs remain, we still have a
15978 // FIXME: Can this really happen?
15979 if (Key
.get()->containsUnexpandedParameterPack() ||
15980 Value
.get()->containsUnexpandedParameterPack())
15981 Element
.EllipsisLoc
= OrigElement
.EllipsisLoc
;
15983 Elements
.push_back(Element
);
15986 // FIXME: Retain a pack expansion if RetainExpansion is true.
15988 // We've finished with this pack expansion.
15992 // Transform and check key.
15993 ExprResult Key
= getDerived().TransformExpr(OrigElement
.Key
);
15994 if (Key
.isInvalid())
15995 return ExprError();
15997 if (Key
.get() != OrigElement
.Key
)
16000 // Transform and check value.
16002 = getDerived().TransformExpr(OrigElement
.Value
);
16003 if (Value
.isInvalid())
16004 return ExprError();
16006 if (Value
.get() != OrigElement
.Value
)
16009 ObjCDictionaryElement Element
= {Key
.get(), Value
.get(), SourceLocation(),
16011 Elements
.push_back(Element
);
16014 if (!getDerived().AlwaysRebuild() && !ArgChanged
)
16015 return SemaRef
.MaybeBindToTemporary(E
);
16017 return getDerived().RebuildObjCDictionaryLiteral(E
->getSourceRange(),
16021 template<typename Derived
>
16023 TreeTransform
<Derived
>::TransformObjCEncodeExpr(ObjCEncodeExpr
*E
) {
16024 TypeSourceInfo
*EncodedTypeInfo
16025 = getDerived().TransformType(E
->getEncodedTypeSourceInfo());
16026 if (!EncodedTypeInfo
)
16027 return ExprError();
16029 if (!getDerived().AlwaysRebuild() &&
16030 EncodedTypeInfo
== E
->getEncodedTypeSourceInfo())
16033 return getDerived().RebuildObjCEncodeExpr(E
->getAtLoc(),
16035 E
->getRParenLoc());
16038 template<typename Derived
>
16039 ExprResult TreeTransform
<Derived
>::
16040 TransformObjCIndirectCopyRestoreExpr(ObjCIndirectCopyRestoreExpr
*E
) {
16041 // This is a kind of implicit conversion, and it needs to get dropped
16042 // and recomputed for the same general reasons that ImplicitCastExprs
16043 // do, as well a more specific one: this expression is only valid when
16044 // it appears *immediately* as an argument expression.
16045 return getDerived().TransformExpr(E
->getSubExpr());
16048 template<typename Derived
>
16049 ExprResult TreeTransform
<Derived
>::
16050 TransformObjCBridgedCastExpr(ObjCBridgedCastExpr
*E
) {
16051 TypeSourceInfo
*TSInfo
16052 = getDerived().TransformType(E
->getTypeInfoAsWritten());
16054 return ExprError();
16056 ExprResult Result
= getDerived().TransformExpr(E
->getSubExpr());
16057 if (Result
.isInvalid())
16058 return ExprError();
16060 if (!getDerived().AlwaysRebuild() &&
16061 TSInfo
== E
->getTypeInfoAsWritten() &&
16062 Result
.get() == E
->getSubExpr())
16065 return SemaRef
.ObjC().BuildObjCBridgedCast(
16066 E
->getLParenLoc(), E
->getBridgeKind(), E
->getBridgeKeywordLoc(), TSInfo
,
16070 template <typename Derived
>
16071 ExprResult TreeTransform
<Derived
>::TransformObjCAvailabilityCheckExpr(
16072 ObjCAvailabilityCheckExpr
*E
) {
16076 template<typename Derived
>
16078 TreeTransform
<Derived
>::TransformObjCMessageExpr(ObjCMessageExpr
*E
) {
16079 // Transform arguments.
16080 bool ArgChanged
= false;
16081 SmallVector
<Expr
*, 8> Args
;
16082 Args
.reserve(E
->getNumArgs());
16083 if (getDerived().TransformExprs(E
->getArgs(), E
->getNumArgs(), false, Args
,
16085 return ExprError();
16087 if (E
->getReceiverKind() == ObjCMessageExpr::Class
) {
16088 // Class message: transform the receiver type.
16089 TypeSourceInfo
*ReceiverTypeInfo
16090 = getDerived().TransformType(E
->getClassReceiverTypeInfo());
16091 if (!ReceiverTypeInfo
)
16092 return ExprError();
16094 // If nothing changed, just retain the existing message send.
16095 if (!getDerived().AlwaysRebuild() &&
16096 ReceiverTypeInfo
== E
->getClassReceiverTypeInfo() && !ArgChanged
)
16097 return SemaRef
.MaybeBindToTemporary(E
);
16099 // Build a new class message send.
16100 SmallVector
<SourceLocation
, 16> SelLocs
;
16101 E
->getSelectorLocs(SelLocs
);
16102 return getDerived().RebuildObjCMessageExpr(ReceiverTypeInfo
,
16105 E
->getMethodDecl(),
16110 else if (E
->getReceiverKind() == ObjCMessageExpr::SuperClass
||
16111 E
->getReceiverKind() == ObjCMessageExpr::SuperInstance
) {
16112 if (!E
->getMethodDecl())
16113 return ExprError();
16115 // Build a new class message send to 'super'.
16116 SmallVector
<SourceLocation
, 16> SelLocs
;
16117 E
->getSelectorLocs(SelLocs
);
16118 return getDerived().RebuildObjCMessageExpr(E
->getSuperLoc(),
16121 E
->getReceiverType(),
16122 E
->getMethodDecl(),
16128 // Instance message: transform the receiver
16129 assert(E
->getReceiverKind() == ObjCMessageExpr::Instance
&&
16130 "Only class and instance messages may be instantiated");
16131 ExprResult Receiver
16132 = getDerived().TransformExpr(E
->getInstanceReceiver());
16133 if (Receiver
.isInvalid())
16134 return ExprError();
16136 // If nothing changed, just retain the existing message send.
16137 if (!getDerived().AlwaysRebuild() &&
16138 Receiver
.get() == E
->getInstanceReceiver() && !ArgChanged
)
16139 return SemaRef
.MaybeBindToTemporary(E
);
16141 // Build a new instance message send.
16142 SmallVector
<SourceLocation
, 16> SelLocs
;
16143 E
->getSelectorLocs(SelLocs
);
16144 return getDerived().RebuildObjCMessageExpr(Receiver
.get(),
16147 E
->getMethodDecl(),
16153 template<typename Derived
>
16155 TreeTransform
<Derived
>::TransformObjCSelectorExpr(ObjCSelectorExpr
*E
) {
16159 template<typename Derived
>
16161 TreeTransform
<Derived
>::TransformObjCProtocolExpr(ObjCProtocolExpr
*E
) {
16165 template<typename Derived
>
16167 TreeTransform
<Derived
>::TransformObjCIvarRefExpr(ObjCIvarRefExpr
*E
) {
16168 // Transform the base expression.
16169 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
16170 if (Base
.isInvalid())
16171 return ExprError();
16173 // We don't need to transform the ivar; it will never change.
16175 // If nothing changed, just retain the existing expression.
16176 if (!getDerived().AlwaysRebuild() &&
16177 Base
.get() == E
->getBase())
16180 return getDerived().RebuildObjCIvarRefExpr(Base
.get(), E
->getDecl(),
16182 E
->isArrow(), E
->isFreeIvar());
16185 template<typename Derived
>
16187 TreeTransform
<Derived
>::TransformObjCPropertyRefExpr(ObjCPropertyRefExpr
*E
) {
16188 // 'super' and types never change. Property never changes. Just
16189 // retain the existing expression.
16190 if (!E
->isObjectReceiver())
16193 // Transform the base expression.
16194 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
16195 if (Base
.isInvalid())
16196 return ExprError();
16198 // We don't need to transform the property; it will never change.
16200 // If nothing changed, just retain the existing expression.
16201 if (!getDerived().AlwaysRebuild() &&
16202 Base
.get() == E
->getBase())
16205 if (E
->isExplicitProperty())
16206 return getDerived().RebuildObjCPropertyRefExpr(Base
.get(),
16207 E
->getExplicitProperty(),
16210 return getDerived().RebuildObjCPropertyRefExpr(Base
.get(),
16211 SemaRef
.Context
.PseudoObjectTy
,
16212 E
->getImplicitPropertyGetter(),
16213 E
->getImplicitPropertySetter(),
16217 template<typename Derived
>
16219 TreeTransform
<Derived
>::TransformObjCSubscriptRefExpr(ObjCSubscriptRefExpr
*E
) {
16220 // Transform the base expression.
16221 ExprResult Base
= getDerived().TransformExpr(E
->getBaseExpr());
16222 if (Base
.isInvalid())
16223 return ExprError();
16225 // Transform the key expression.
16226 ExprResult Key
= getDerived().TransformExpr(E
->getKeyExpr());
16227 if (Key
.isInvalid())
16228 return ExprError();
16230 // If nothing changed, just retain the existing expression.
16231 if (!getDerived().AlwaysRebuild() &&
16232 Key
.get() == E
->getKeyExpr() && Base
.get() == E
->getBaseExpr())
16235 return getDerived().RebuildObjCSubscriptRefExpr(E
->getRBracket(),
16236 Base
.get(), Key
.get(),
16237 E
->getAtIndexMethodDecl(),
16238 E
->setAtIndexMethodDecl());
16241 template<typename Derived
>
16243 TreeTransform
<Derived
>::TransformObjCIsaExpr(ObjCIsaExpr
*E
) {
16244 // Transform the base expression.
16245 ExprResult Base
= getDerived().TransformExpr(E
->getBase());
16246 if (Base
.isInvalid())
16247 return ExprError();
16249 // If nothing changed, just retain the existing expression.
16250 if (!getDerived().AlwaysRebuild() &&
16251 Base
.get() == E
->getBase())
16254 return getDerived().RebuildObjCIsaExpr(Base
.get(), E
->getIsaMemberLoc(),
16259 template<typename Derived
>
16261 TreeTransform
<Derived
>::TransformShuffleVectorExpr(ShuffleVectorExpr
*E
) {
16262 bool ArgumentChanged
= false;
16263 SmallVector
<Expr
*, 8> SubExprs
;
16264 SubExprs
.reserve(E
->getNumSubExprs());
16265 if (getDerived().TransformExprs(E
->getSubExprs(), E
->getNumSubExprs(), false,
16266 SubExprs
, &ArgumentChanged
))
16267 return ExprError();
16269 if (!getDerived().AlwaysRebuild() &&
16273 return getDerived().RebuildShuffleVectorExpr(E
->getBuiltinLoc(),
16275 E
->getRParenLoc());
16278 template<typename Derived
>
16280 TreeTransform
<Derived
>::TransformConvertVectorExpr(ConvertVectorExpr
*E
) {
16281 ExprResult SrcExpr
= getDerived().TransformExpr(E
->getSrcExpr());
16282 if (SrcExpr
.isInvalid())
16283 return ExprError();
16285 TypeSourceInfo
*Type
= getDerived().TransformType(E
->getTypeSourceInfo());
16287 return ExprError();
16289 if (!getDerived().AlwaysRebuild() &&
16290 Type
== E
->getTypeSourceInfo() &&
16291 SrcExpr
.get() == E
->getSrcExpr())
16294 return getDerived().RebuildConvertVectorExpr(E
->getBuiltinLoc(),
16295 SrcExpr
.get(), Type
,
16296 E
->getRParenLoc());
16299 template<typename Derived
>
16301 TreeTransform
<Derived
>::TransformBlockExpr(BlockExpr
*E
) {
16302 BlockDecl
*oldBlock
= E
->getBlockDecl();
16304 SemaRef
.ActOnBlockStart(E
->getCaretLocation(), /*Scope=*/nullptr);
16305 BlockScopeInfo
*blockScope
= SemaRef
.getCurBlock();
16307 blockScope
->TheDecl
->setIsVariadic(oldBlock
->isVariadic());
16308 blockScope
->TheDecl
->setBlockMissingReturnType(
16309 oldBlock
->blockMissingReturnType());
16311 SmallVector
<ParmVarDecl
*, 4> params
;
16312 SmallVector
<QualType
, 4> paramTypes
;
16314 const FunctionProtoType
*exprFunctionType
= E
->getFunctionType();
16316 // Parameter substitution.
16317 Sema::ExtParameterInfoBuilder extParamInfos
;
16318 if (getDerived().TransformFunctionTypeParams(
16319 E
->getCaretLocation(), oldBlock
->parameters(), nullptr,
16320 exprFunctionType
->getExtParameterInfosOrNull(), paramTypes
, ¶ms
,
16322 getSema().ActOnBlockError(E
->getCaretLocation(), /*Scope=*/nullptr);
16323 return ExprError();
16326 QualType exprResultType
=
16327 getDerived().TransformType(exprFunctionType
->getReturnType());
16329 auto epi
= exprFunctionType
->getExtProtoInfo();
16330 epi
.ExtParameterInfos
= extParamInfos
.getPointerOrNull(paramTypes
.size());
16332 QualType functionType
=
16333 getDerived().RebuildFunctionProtoType(exprResultType
, paramTypes
, epi
);
16334 blockScope
->FunctionType
= functionType
;
16336 // Set the parameters on the block decl.
16337 if (!params
.empty())
16338 blockScope
->TheDecl
->setParams(params
);
16340 if (!oldBlock
->blockMissingReturnType()) {
16341 blockScope
->HasImplicitReturnType
= false;
16342 blockScope
->ReturnType
= exprResultType
;
16345 // Transform the body
16346 StmtResult body
= getDerived().TransformStmt(E
->getBody());
16347 if (body
.isInvalid()) {
16348 getSema().ActOnBlockError(E
->getCaretLocation(), /*Scope=*/nullptr);
16349 return ExprError();
16353 // In builds with assertions, make sure that we captured everything we
16354 // captured before.
16355 if (!SemaRef
.getDiagnostics().hasErrorOccurred()) {
16356 for (const auto &I
: oldBlock
->captures()) {
16357 VarDecl
*oldCapture
= I
.getVariable();
16359 // Ignore parameter packs.
16360 if (oldCapture
->isParameterPack())
16363 VarDecl
*newCapture
=
16364 cast
<VarDecl
>(getDerived().TransformDecl(E
->getCaretLocation(),
16366 assert(blockScope
->CaptureMap
.count(newCapture
));
16369 // The this pointer may not be captured by the instantiated block, even when
16370 // it's captured by the original block, if the expression causing the
16371 // capture is in the discarded branch of a constexpr if statement.
16372 assert((!blockScope
->isCXXThisCaptured() || oldBlock
->capturesCXXThis()) &&
16373 "this pointer isn't captured in the old block");
16377 return SemaRef
.ActOnBlockStmtExpr(E
->getCaretLocation(), body
.get(),
16378 /*Scope=*/nullptr);
16381 template<typename Derived
>
16383 TreeTransform
<Derived
>::TransformAsTypeExpr(AsTypeExpr
*E
) {
16384 ExprResult SrcExpr
= getDerived().TransformExpr(E
->getSrcExpr());
16385 if (SrcExpr
.isInvalid())
16386 return ExprError();
16388 QualType Type
= getDerived().TransformType(E
->getType());
16390 return SemaRef
.BuildAsTypeExpr(SrcExpr
.get(), Type
, E
->getBuiltinLoc(),
16391 E
->getRParenLoc());
16394 template<typename Derived
>
16396 TreeTransform
<Derived
>::TransformAtomicExpr(AtomicExpr
*E
) {
16397 bool ArgumentChanged
= false;
16398 SmallVector
<Expr
*, 8> SubExprs
;
16399 SubExprs
.reserve(E
->getNumSubExprs());
16400 if (getDerived().TransformExprs(E
->getSubExprs(), E
->getNumSubExprs(), false,
16401 SubExprs
, &ArgumentChanged
))
16402 return ExprError();
16404 if (!getDerived().AlwaysRebuild() &&
16408 return getDerived().RebuildAtomicExpr(E
->getBuiltinLoc(), SubExprs
,
16409 E
->getOp(), E
->getRParenLoc());
16412 //===----------------------------------------------------------------------===//
16413 // Type reconstruction
16414 //===----------------------------------------------------------------------===//
16416 template<typename Derived
>
16417 QualType TreeTransform
<Derived
>::RebuildPointerType(QualType PointeeType
,
16418 SourceLocation Star
) {
16419 return SemaRef
.BuildPointerType(PointeeType
, Star
,
16420 getDerived().getBaseEntity());
16423 template<typename Derived
>
16424 QualType TreeTransform
<Derived
>::RebuildBlockPointerType(QualType PointeeType
,
16425 SourceLocation Star
) {
16426 return SemaRef
.BuildBlockPointerType(PointeeType
, Star
,
16427 getDerived().getBaseEntity());
16430 template<typename Derived
>
16432 TreeTransform
<Derived
>::RebuildReferenceType(QualType ReferentType
,
16433 bool WrittenAsLValue
,
16434 SourceLocation Sigil
) {
16435 return SemaRef
.BuildReferenceType(ReferentType
, WrittenAsLValue
,
16436 Sigil
, getDerived().getBaseEntity());
16439 template<typename Derived
>
16441 TreeTransform
<Derived
>::RebuildMemberPointerType(QualType PointeeType
,
16442 QualType ClassType
,
16443 SourceLocation Sigil
) {
16444 return SemaRef
.BuildMemberPointerType(PointeeType
, ClassType
, Sigil
,
16445 getDerived().getBaseEntity());
16448 template<typename Derived
>
16449 QualType TreeTransform
<Derived
>::RebuildObjCTypeParamType(
16450 const ObjCTypeParamDecl
*Decl
,
16451 SourceLocation ProtocolLAngleLoc
,
16452 ArrayRef
<ObjCProtocolDecl
*> Protocols
,
16453 ArrayRef
<SourceLocation
> ProtocolLocs
,
16454 SourceLocation ProtocolRAngleLoc
) {
16455 return SemaRef
.ObjC().BuildObjCTypeParamType(
16456 Decl
, ProtocolLAngleLoc
, Protocols
, ProtocolLocs
, ProtocolRAngleLoc
,
16457 /*FailOnError=*/true);
16460 template<typename Derived
>
16461 QualType TreeTransform
<Derived
>::RebuildObjCObjectType(
16463 SourceLocation Loc
,
16464 SourceLocation TypeArgsLAngleLoc
,
16465 ArrayRef
<TypeSourceInfo
*> TypeArgs
,
16466 SourceLocation TypeArgsRAngleLoc
,
16467 SourceLocation ProtocolLAngleLoc
,
16468 ArrayRef
<ObjCProtocolDecl
*> Protocols
,
16469 ArrayRef
<SourceLocation
> ProtocolLocs
,
16470 SourceLocation ProtocolRAngleLoc
) {
16471 return SemaRef
.ObjC().BuildObjCObjectType(
16472 BaseType
, Loc
, TypeArgsLAngleLoc
, TypeArgs
, TypeArgsRAngleLoc
,
16473 ProtocolLAngleLoc
, Protocols
, ProtocolLocs
, ProtocolRAngleLoc
,
16474 /*FailOnError=*/true,
16475 /*Rebuilding=*/true);
16478 template<typename Derived
>
16479 QualType TreeTransform
<Derived
>::RebuildObjCObjectPointerType(
16480 QualType PointeeType
,
16481 SourceLocation Star
) {
16482 return SemaRef
.Context
.getObjCObjectPointerType(PointeeType
);
16485 template <typename Derived
>
16486 QualType TreeTransform
<Derived
>::RebuildArrayType(
16487 QualType ElementType
, ArraySizeModifier SizeMod
, const llvm::APInt
*Size
,
16488 Expr
*SizeExpr
, unsigned IndexTypeQuals
, SourceRange BracketsRange
) {
16489 if (SizeExpr
|| !Size
)
16490 return SemaRef
.BuildArrayType(ElementType
, SizeMod
, SizeExpr
,
16491 IndexTypeQuals
, BracketsRange
,
16492 getDerived().getBaseEntity());
16494 QualType Types
[] = {
16495 SemaRef
.Context
.UnsignedCharTy
, SemaRef
.Context
.UnsignedShortTy
,
16496 SemaRef
.Context
.UnsignedIntTy
, SemaRef
.Context
.UnsignedLongTy
,
16497 SemaRef
.Context
.UnsignedLongLongTy
, SemaRef
.Context
.UnsignedInt128Ty
16500 for (const auto &T
: Types
)
16501 if (Size
->getBitWidth() == SemaRef
.Context
.getIntWidth(T
)) {
16506 // Note that we can return a VariableArrayType here in the case where
16507 // the element type was a dependent VariableArrayType.
16508 IntegerLiteral
*ArraySize
16509 = IntegerLiteral::Create(SemaRef
.Context
, *Size
, SizeType
,
16510 /*FIXME*/BracketsRange
.getBegin());
16511 return SemaRef
.BuildArrayType(ElementType
, SizeMod
, ArraySize
,
16512 IndexTypeQuals
, BracketsRange
,
16513 getDerived().getBaseEntity());
16516 template <typename Derived
>
16517 QualType TreeTransform
<Derived
>::RebuildConstantArrayType(
16518 QualType ElementType
, ArraySizeModifier SizeMod
, const llvm::APInt
&Size
,
16519 Expr
*SizeExpr
, unsigned IndexTypeQuals
, SourceRange BracketsRange
) {
16520 return getDerived().RebuildArrayType(ElementType
, SizeMod
, &Size
, SizeExpr
,
16521 IndexTypeQuals
, BracketsRange
);
16524 template <typename Derived
>
16525 QualType TreeTransform
<Derived
>::RebuildIncompleteArrayType(
16526 QualType ElementType
, ArraySizeModifier SizeMod
, unsigned IndexTypeQuals
,
16527 SourceRange BracketsRange
) {
16528 return getDerived().RebuildArrayType(ElementType
, SizeMod
, nullptr, nullptr,
16529 IndexTypeQuals
, BracketsRange
);
16532 template <typename Derived
>
16533 QualType TreeTransform
<Derived
>::RebuildVariableArrayType(
16534 QualType ElementType
, ArraySizeModifier SizeMod
, Expr
*SizeExpr
,
16535 unsigned IndexTypeQuals
, SourceRange BracketsRange
) {
16536 return getDerived().RebuildArrayType(ElementType
, SizeMod
, nullptr,
16538 IndexTypeQuals
, BracketsRange
);
16541 template <typename Derived
>
16542 QualType TreeTransform
<Derived
>::RebuildDependentSizedArrayType(
16543 QualType ElementType
, ArraySizeModifier SizeMod
, Expr
*SizeExpr
,
16544 unsigned IndexTypeQuals
, SourceRange BracketsRange
) {
16545 return getDerived().RebuildArrayType(ElementType
, SizeMod
, nullptr,
16547 IndexTypeQuals
, BracketsRange
);
16550 template <typename Derived
>
16551 QualType TreeTransform
<Derived
>::RebuildDependentAddressSpaceType(
16552 QualType PointeeType
, Expr
*AddrSpaceExpr
, SourceLocation AttributeLoc
) {
16553 return SemaRef
.BuildAddressSpaceAttr(PointeeType
, AddrSpaceExpr
,
16557 template <typename Derived
>
16558 QualType TreeTransform
<Derived
>::RebuildVectorType(QualType ElementType
,
16559 unsigned NumElements
,
16560 VectorKind VecKind
) {
16561 // FIXME: semantic checking!
16562 return SemaRef
.Context
.getVectorType(ElementType
, NumElements
, VecKind
);
16565 template <typename Derived
>
16566 QualType TreeTransform
<Derived
>::RebuildDependentVectorType(
16567 QualType ElementType
, Expr
*SizeExpr
, SourceLocation AttributeLoc
,
16568 VectorKind VecKind
) {
16569 return SemaRef
.BuildVectorType(ElementType
, SizeExpr
, AttributeLoc
);
16572 template<typename Derived
>
16573 QualType TreeTransform
<Derived
>::RebuildExtVectorType(QualType ElementType
,
16574 unsigned NumElements
,
16575 SourceLocation AttributeLoc
) {
16576 llvm::APInt
numElements(SemaRef
.Context
.getIntWidth(SemaRef
.Context
.IntTy
),
16577 NumElements
, true);
16578 IntegerLiteral
*VectorSize
16579 = IntegerLiteral::Create(SemaRef
.Context
, numElements
, SemaRef
.Context
.IntTy
,
16581 return SemaRef
.BuildExtVectorType(ElementType
, VectorSize
, AttributeLoc
);
16584 template<typename Derived
>
16586 TreeTransform
<Derived
>::RebuildDependentSizedExtVectorType(QualType ElementType
,
16588 SourceLocation AttributeLoc
) {
16589 return SemaRef
.BuildExtVectorType(ElementType
, SizeExpr
, AttributeLoc
);
16592 template <typename Derived
>
16593 QualType TreeTransform
<Derived
>::RebuildConstantMatrixType(
16594 QualType ElementType
, unsigned NumRows
, unsigned NumColumns
) {
16595 return SemaRef
.Context
.getConstantMatrixType(ElementType
, NumRows
,
16599 template <typename Derived
>
16600 QualType TreeTransform
<Derived
>::RebuildDependentSizedMatrixType(
16601 QualType ElementType
, Expr
*RowExpr
, Expr
*ColumnExpr
,
16602 SourceLocation AttributeLoc
) {
16603 return SemaRef
.BuildMatrixType(ElementType
, RowExpr
, ColumnExpr
,
16607 template<typename Derived
>
16608 QualType TreeTransform
<Derived
>::RebuildFunctionProtoType(
16610 MutableArrayRef
<QualType
> ParamTypes
,
16611 const FunctionProtoType::ExtProtoInfo
&EPI
) {
16612 return SemaRef
.BuildFunctionType(T
, ParamTypes
,
16613 getDerived().getBaseLocation(),
16614 getDerived().getBaseEntity(),
16618 template<typename Derived
>
16619 QualType TreeTransform
<Derived
>::RebuildFunctionNoProtoType(QualType T
) {
16620 return SemaRef
.Context
.getFunctionNoProtoType(T
);
16623 template<typename Derived
>
16624 QualType TreeTransform
<Derived
>::RebuildUnresolvedUsingType(SourceLocation Loc
,
16626 assert(D
&& "no decl found");
16627 if (D
->isInvalidDecl()) return QualType();
16629 // FIXME: Doesn't account for ObjCInterfaceDecl!
16630 if (auto *UPD
= dyn_cast
<UsingPackDecl
>(D
)) {
16631 // A valid resolved using typename pack expansion decl can have multiple
16632 // UsingDecls, but they must each have exactly one type, and it must be
16633 // the same type in every case. But we must have at least one expansion!
16634 if (UPD
->expansions().empty()) {
16635 getSema().Diag(Loc
, diag::err_using_pack_expansion_empty
)
16636 << UPD
->isCXXClassMember() << UPD
;
16640 // We might still have some unresolved types. Try to pick a resolved type
16641 // if we can. The final instantiation will check that the remaining
16642 // unresolved types instantiate to the type we pick.
16643 QualType FallbackT
;
16645 for (auto *E
: UPD
->expansions()) {
16646 QualType ThisT
= RebuildUnresolvedUsingType(Loc
, E
);
16647 if (ThisT
.isNull())
16649 else if (ThisT
->getAs
<UnresolvedUsingType
>())
16651 else if (T
.isNull())
16654 assert(getSema().Context
.hasSameType(ThisT
, T
) &&
16655 "mismatched resolved types in using pack expansion");
16657 return T
.isNull() ? FallbackT
: T
;
16658 } else if (auto *Using
= dyn_cast
<UsingDecl
>(D
)) {
16659 assert(Using
->hasTypename() &&
16660 "UnresolvedUsingTypenameDecl transformed to non-typename using");
16662 // A valid resolved using typename decl points to exactly one type decl.
16663 assert(++Using
->shadow_begin() == Using
->shadow_end());
16665 UsingShadowDecl
*Shadow
= *Using
->shadow_begin();
16666 if (SemaRef
.DiagnoseUseOfDecl(Shadow
->getTargetDecl(), Loc
))
16668 return SemaRef
.Context
.getUsingType(
16669 Shadow
, SemaRef
.Context
.getTypeDeclType(
16670 cast
<TypeDecl
>(Shadow
->getTargetDecl())));
16672 assert(isa
<UnresolvedUsingTypenameDecl
>(D
) &&
16673 "UnresolvedUsingTypenameDecl transformed to non-using decl");
16674 return SemaRef
.Context
.getTypeDeclType(
16675 cast
<UnresolvedUsingTypenameDecl
>(D
));
16679 template <typename Derived
>
16680 QualType TreeTransform
<Derived
>::RebuildTypeOfExprType(Expr
*E
, SourceLocation
,
16682 return SemaRef
.BuildTypeofExprType(E
, Kind
);
16685 template<typename Derived
>
16686 QualType TreeTransform
<Derived
>::RebuildTypeOfType(QualType Underlying
,
16688 return SemaRef
.Context
.getTypeOfType(Underlying
, Kind
);
16691 template <typename Derived
>
16692 QualType TreeTransform
<Derived
>::RebuildDecltypeType(Expr
*E
, SourceLocation
) {
16693 return SemaRef
.BuildDecltypeType(E
);
16696 template <typename Derived
>
16697 QualType TreeTransform
<Derived
>::RebuildPackIndexingType(
16698 QualType Pattern
, Expr
*IndexExpr
, SourceLocation Loc
,
16699 SourceLocation EllipsisLoc
, bool FullySubstituted
,
16700 ArrayRef
<QualType
> Expansions
) {
16701 return SemaRef
.BuildPackIndexingType(Pattern
, IndexExpr
, Loc
, EllipsisLoc
,
16702 FullySubstituted
, Expansions
);
16705 template<typename Derived
>
16706 QualType TreeTransform
<Derived
>::RebuildUnaryTransformType(QualType BaseType
,
16707 UnaryTransformType::UTTKind UKind
,
16708 SourceLocation Loc
) {
16709 return SemaRef
.BuildUnaryTransformType(BaseType
, UKind
, Loc
);
16712 template<typename Derived
>
16713 QualType TreeTransform
<Derived
>::RebuildTemplateSpecializationType(
16714 TemplateName Template
,
16715 SourceLocation TemplateNameLoc
,
16716 TemplateArgumentListInfo
&TemplateArgs
) {
16717 return SemaRef
.CheckTemplateIdType(Template
, TemplateNameLoc
, TemplateArgs
);
16720 template<typename Derived
>
16721 QualType TreeTransform
<Derived
>::RebuildAtomicType(QualType ValueType
,
16722 SourceLocation KWLoc
) {
16723 return SemaRef
.BuildAtomicType(ValueType
, KWLoc
);
16726 template<typename Derived
>
16727 QualType TreeTransform
<Derived
>::RebuildPipeType(QualType ValueType
,
16728 SourceLocation KWLoc
,
16730 return isReadPipe
? SemaRef
.BuildReadPipeType(ValueType
, KWLoc
)
16731 : SemaRef
.BuildWritePipeType(ValueType
, KWLoc
);
16734 template <typename Derived
>
16735 QualType TreeTransform
<Derived
>::RebuildBitIntType(bool IsUnsigned
,
16737 SourceLocation Loc
) {
16738 llvm::APInt
NumBitsAP(SemaRef
.Context
.getIntWidth(SemaRef
.Context
.IntTy
),
16740 IntegerLiteral
*Bits
= IntegerLiteral::Create(SemaRef
.Context
, NumBitsAP
,
16741 SemaRef
.Context
.IntTy
, Loc
);
16742 return SemaRef
.BuildBitIntType(IsUnsigned
, Bits
, Loc
);
16745 template <typename Derived
>
16746 QualType TreeTransform
<Derived
>::RebuildDependentBitIntType(
16747 bool IsUnsigned
, Expr
*NumBitsExpr
, SourceLocation Loc
) {
16748 return SemaRef
.BuildBitIntType(IsUnsigned
, NumBitsExpr
, Loc
);
16751 template<typename Derived
>
16753 TreeTransform
<Derived
>::RebuildTemplateName(CXXScopeSpec
&SS
,
16755 TemplateDecl
*Template
) {
16756 return SemaRef
.Context
.getQualifiedTemplateName(SS
.getScopeRep(), TemplateKW
,
16757 TemplateName(Template
));
16760 template<typename Derived
>
16762 TreeTransform
<Derived
>::RebuildTemplateName(CXXScopeSpec
&SS
,
16763 SourceLocation TemplateKWLoc
,
16764 const IdentifierInfo
&Name
,
16765 SourceLocation NameLoc
,
16766 QualType ObjectType
,
16767 NamedDecl
*FirstQualifierInScope
,
16768 bool AllowInjectedClassName
) {
16769 UnqualifiedId TemplateName
;
16770 TemplateName
.setIdentifier(&Name
, NameLoc
);
16771 Sema::TemplateTy Template
;
16772 getSema().ActOnTemplateName(/*Scope=*/nullptr, SS
, TemplateKWLoc
,
16773 TemplateName
, ParsedType::make(ObjectType
),
16774 /*EnteringContext=*/false, Template
,
16775 AllowInjectedClassName
);
16776 return Template
.get();
16779 template<typename Derived
>
16781 TreeTransform
<Derived
>::RebuildTemplateName(CXXScopeSpec
&SS
,
16782 SourceLocation TemplateKWLoc
,
16783 OverloadedOperatorKind Operator
,
16784 SourceLocation NameLoc
,
16785 QualType ObjectType
,
16786 bool AllowInjectedClassName
) {
16787 UnqualifiedId Name
;
16788 // FIXME: Bogus location information.
16789 SourceLocation SymbolLocations
[3] = { NameLoc
, NameLoc
, NameLoc
};
16790 Name
.setOperatorFunctionId(NameLoc
, Operator
, SymbolLocations
);
16791 Sema::TemplateTy Template
;
16792 getSema().ActOnTemplateName(
16793 /*Scope=*/nullptr, SS
, TemplateKWLoc
, Name
, ParsedType::make(ObjectType
),
16794 /*EnteringContext=*/false, Template
, AllowInjectedClassName
);
16795 return Template
.get();
16798 template <typename Derived
>
16799 ExprResult TreeTransform
<Derived
>::RebuildCXXOperatorCallExpr(
16800 OverloadedOperatorKind Op
, SourceLocation OpLoc
, SourceLocation CalleeLoc
,
16801 bool RequiresADL
, const UnresolvedSetImpl
&Functions
, Expr
*First
,
16803 bool isPostIncDec
= Second
&& (Op
== OO_PlusPlus
|| Op
== OO_MinusMinus
);
16805 if (First
->getObjectKind() == OK_ObjCProperty
) {
16806 BinaryOperatorKind Opc
= BinaryOperator::getOverloadedOpcode(Op
);
16807 if (BinaryOperator::isAssignmentOp(Opc
))
16808 return SemaRef
.PseudoObject().checkAssignment(/*Scope=*/nullptr, OpLoc
,
16809 Opc
, First
, Second
);
16810 ExprResult Result
= SemaRef
.CheckPlaceholderExpr(First
);
16811 if (Result
.isInvalid())
16812 return ExprError();
16813 First
= Result
.get();
16816 if (Second
&& Second
->getObjectKind() == OK_ObjCProperty
) {
16817 ExprResult Result
= SemaRef
.CheckPlaceholderExpr(Second
);
16818 if (Result
.isInvalid())
16819 return ExprError();
16820 Second
= Result
.get();
16823 // Determine whether this should be a builtin operation.
16824 if (Op
== OO_Subscript
) {
16825 if (!First
->getType()->isOverloadableType() &&
16826 !Second
->getType()->isOverloadableType())
16827 return getSema().CreateBuiltinArraySubscriptExpr(First
, CalleeLoc
, Second
,
16829 } else if (Op
== OO_Arrow
) {
16830 // It is possible that the type refers to a RecoveryExpr created earlier
16831 // in the tree transformation.
16832 if (First
->getType()->isDependentType())
16833 return ExprError();
16834 // -> is never a builtin operation.
16835 return SemaRef
.BuildOverloadedArrowExpr(nullptr, First
, OpLoc
);
16836 } else if (Second
== nullptr || isPostIncDec
) {
16837 if (!First
->getType()->isOverloadableType() ||
16838 (Op
== OO_Amp
&& getSema().isQualifiedMemberAccess(First
))) {
16839 // The argument is not of overloadable type, or this is an expression
16840 // of the form &Class::member, so try to create a built-in unary
16842 UnaryOperatorKind Opc
16843 = UnaryOperator::getOverloadedOpcode(Op
, isPostIncDec
);
16845 return getSema().CreateBuiltinUnaryOp(OpLoc
, Opc
, First
);
16848 if (!First
->isTypeDependent() && !Second
->isTypeDependent() &&
16849 !First
->getType()->isOverloadableType() &&
16850 !Second
->getType()->isOverloadableType()) {
16851 // Neither of the arguments is type-dependent or has an overloadable
16852 // type, so try to create a built-in binary operation.
16853 BinaryOperatorKind Opc
= BinaryOperator::getOverloadedOpcode(Op
);
16855 = SemaRef
.CreateBuiltinBinOp(OpLoc
, Opc
, First
, Second
);
16856 if (Result
.isInvalid())
16857 return ExprError();
16863 // Create the overloaded operator invocation for unary operators.
16864 if (!Second
|| isPostIncDec
) {
16865 UnaryOperatorKind Opc
16866 = UnaryOperator::getOverloadedOpcode(Op
, isPostIncDec
);
16867 return SemaRef
.CreateOverloadedUnaryOp(OpLoc
, Opc
, Functions
, First
,
16871 // Create the overloaded operator invocation for binary operators.
16872 BinaryOperatorKind Opc
= BinaryOperator::getOverloadedOpcode(Op
);
16873 ExprResult Result
= SemaRef
.CreateOverloadedBinOp(OpLoc
, Opc
, Functions
,
16874 First
, Second
, RequiresADL
);
16875 if (Result
.isInvalid())
16876 return ExprError();
16881 template<typename Derived
>
16883 TreeTransform
<Derived
>::RebuildCXXPseudoDestructorExpr(Expr
*Base
,
16884 SourceLocation OperatorLoc
,
16887 TypeSourceInfo
*ScopeType
,
16888 SourceLocation CCLoc
,
16889 SourceLocation TildeLoc
,
16890 PseudoDestructorTypeStorage Destroyed
) {
16891 QualType BaseType
= Base
->getType();
16892 if (Base
->isTypeDependent() || Destroyed
.getIdentifier() ||
16893 (!isArrow
&& !BaseType
->getAs
<RecordType
>()) ||
16894 (isArrow
&& BaseType
->getAs
<PointerType
>() &&
16895 !BaseType
->castAs
<PointerType
>()->getPointeeType()
16896 ->template getAs
<RecordType
>())){
16897 // This pseudo-destructor expression is still a pseudo-destructor.
16898 return SemaRef
.BuildPseudoDestructorExpr(
16899 Base
, OperatorLoc
, isArrow
? tok::arrow
: tok::period
, SS
, ScopeType
,
16900 CCLoc
, TildeLoc
, Destroyed
);
16903 TypeSourceInfo
*DestroyedType
= Destroyed
.getTypeSourceInfo();
16904 DeclarationName
Name(SemaRef
.Context
.DeclarationNames
.getCXXDestructorName(
16905 SemaRef
.Context
.getCanonicalType(DestroyedType
->getType())));
16906 DeclarationNameInfo
NameInfo(Name
, Destroyed
.getLocation());
16907 NameInfo
.setNamedTypeInfo(DestroyedType
);
16909 // The scope type is now known to be a valid nested name specifier
16910 // component. Tack it on to the end of the nested name specifier.
16912 if (!ScopeType
->getType()->getAs
<TagType
>()) {
16913 getSema().Diag(ScopeType
->getTypeLoc().getBeginLoc(),
16914 diag::err_expected_class_or_namespace
)
16915 << ScopeType
->getType() << getSema().getLangOpts().CPlusPlus
;
16916 return ExprError();
16918 SS
.Extend(SemaRef
.Context
, SourceLocation(), ScopeType
->getTypeLoc(),
16922 SourceLocation TemplateKWLoc
; // FIXME: retrieve it from caller.
16923 return getSema().BuildMemberReferenceExpr(Base
, BaseType
,
16924 OperatorLoc
, isArrow
,
16926 /*FIXME: FirstQualifier*/ nullptr,
16928 /*TemplateArgs*/ nullptr,
16932 template<typename Derived
>
16934 TreeTransform
<Derived
>::TransformCapturedStmt(CapturedStmt
*S
) {
16935 SourceLocation Loc
= S
->getBeginLoc();
16936 CapturedDecl
*CD
= S
->getCapturedDecl();
16937 unsigned NumParams
= CD
->getNumParams();
16938 unsigned ContextParamPos
= CD
->getContextParamPosition();
16939 SmallVector
<Sema::CapturedParamNameType
, 4> Params
;
16940 for (unsigned I
= 0; I
< NumParams
; ++I
) {
16941 if (I
!= ContextParamPos
) {
16944 CD
->getParam(I
)->getName(),
16945 getDerived().TransformType(CD
->getParam(I
)->getType())));
16947 Params
.push_back(std::make_pair(StringRef(), QualType()));
16950 getSema().ActOnCapturedRegionStart(Loc
, /*CurScope*/nullptr,
16951 S
->getCapturedRegionKind(), Params
);
16954 Sema::CompoundScopeRAII
CompoundScope(getSema());
16955 Body
= getDerived().TransformStmt(S
->getCapturedStmt());
16958 if (Body
.isInvalid()) {
16959 getSema().ActOnCapturedRegionError();
16960 return StmtError();
16963 return getSema().ActOnCapturedRegionEnd(Body
.get());
16966 template <typename Derived
>
16967 ExprResult TreeTransform
<Derived
>::TransformHLSLOutArgExpr(HLSLOutArgExpr
*E
) {
16968 // We can transform the base expression and allow argument resolution to fill
16970 return getDerived().TransformExpr(E
->getArgLValue());
16973 } // end namespace clang
16975 #endif // LLVM_CLANG_LIB_SEMA_TREETRANSFORM_H