clang 22.0.0git
StmtProfile.cpp
Go to the documentation of this file.
1//===---- StmtProfile.cpp - Profile implementation for Stmt ASTs ----------===//
2//
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//
7//===----------------------------------------------------------------------===//
8//
9// This file implements the Stmt::Profile method, which builds a unique bit
10// representation that identifies a statement/expression.
11//
12//===----------------------------------------------------------------------===//
14#include "clang/AST/DeclCXX.h"
15#include "clang/AST/DeclObjC.h"
17#include "clang/AST/Expr.h"
18#include "clang/AST/ExprCXX.h"
19#include "clang/AST/ExprObjC.h"
21#include "clang/AST/ODRHash.h"
24#include "llvm/ADT/FoldingSet.h"
25using namespace clang;
26
27namespace {
28 class StmtProfiler : public ConstStmtVisitor<StmtProfiler> {
29 protected:
30 llvm::FoldingSetNodeID &ID;
31 bool Canonical;
32 bool ProfileLambdaExpr;
33
34 public:
35 StmtProfiler(llvm::FoldingSetNodeID &ID, bool Canonical,
36 bool ProfileLambdaExpr)
37 : ID(ID), Canonical(Canonical), ProfileLambdaExpr(ProfileLambdaExpr) {}
38
39 virtual ~StmtProfiler() {}
40
41 void VisitStmt(const Stmt *S);
42
43 void VisitStmtNoChildren(const Stmt *S) {
44 HandleStmtClass(S->getStmtClass());
45 }
46
47 virtual void HandleStmtClass(Stmt::StmtClass SC) = 0;
48
49#define STMT(Node, Base) void Visit##Node(const Node *S);
50#include "clang/AST/StmtNodes.inc"
51
52 /// Visit a declaration that is referenced within an expression
53 /// or statement.
54 virtual void VisitDecl(const Decl *D) = 0;
55
56 /// Visit a type that is referenced within an expression or
57 /// statement.
58 virtual void VisitType(QualType T) = 0;
59
60 /// Visit a name that occurs within an expression or statement.
61 virtual void VisitName(DeclarationName Name, bool TreatAsDecl = false) = 0;
62
63 /// Visit identifiers that are not in Decl's or Type's.
64 virtual void VisitIdentifierInfo(const IdentifierInfo *II) = 0;
65
66 /// Visit a nested-name-specifier that occurs within an expression
67 /// or statement.
68 virtual void VisitNestedNameSpecifier(NestedNameSpecifier NNS) = 0;
69
70 /// Visit a template name that occurs within an expression or
71 /// statement.
72 virtual void VisitTemplateName(TemplateName Name) = 0;
73
74 /// Visit template arguments that occur within an expression or
75 /// statement.
76 void VisitTemplateArguments(const TemplateArgumentLoc *Args,
77 unsigned NumArgs);
78
79 /// Visit a single template argument.
80 void VisitTemplateArgument(const TemplateArgument &Arg);
81 };
82
83 class StmtProfilerWithPointers : public StmtProfiler {
84 const ASTContext &Context;
85
86 public:
87 StmtProfilerWithPointers(llvm::FoldingSetNodeID &ID,
88 const ASTContext &Context, bool Canonical,
89 bool ProfileLambdaExpr)
90 : StmtProfiler(ID, Canonical, ProfileLambdaExpr), Context(Context) {}
91
92 private:
93 void HandleStmtClass(Stmt::StmtClass SC) override {
94 ID.AddInteger(SC);
95 }
96
97 void VisitDecl(const Decl *D) override {
98 ID.AddInteger(D ? D->getKind() : 0);
99
100 if (Canonical && D) {
101 if (const NonTypeTemplateParmDecl *NTTP =
102 dyn_cast<NonTypeTemplateParmDecl>(D)) {
103 ID.AddInteger(NTTP->getDepth());
104 ID.AddInteger(NTTP->getIndex());
105 ID.AddBoolean(NTTP->isParameterPack());
106 // C++20 [temp.over.link]p6:
107 // Two template-parameters are equivalent under the following
108 // conditions: [...] if they declare non-type template parameters,
109 // they have equivalent types ignoring the use of type-constraints
110 // for placeholder types
111 //
112 // TODO: Why do we need to include the type in the profile? It's not
113 // part of the mangling.
114 VisitType(Context.getUnconstrainedType(NTTP->getType()));
115 return;
116 }
117
118 if (const ParmVarDecl *Parm = dyn_cast<ParmVarDecl>(D)) {
119 // The Itanium C++ ABI uses the type, scope depth, and scope
120 // index of a parameter when mangling expressions that involve
121 // function parameters, so we will use the parameter's type for
122 // establishing function parameter identity. That way, our
123 // definition of "equivalent" (per C++ [temp.over.link]) is at
124 // least as strong as the definition of "equivalent" used for
125 // name mangling.
126 //
127 // TODO: The Itanium C++ ABI only uses the top-level cv-qualifiers,
128 // not the entirety of the type.
129 VisitType(Parm->getType());
130 ID.AddInteger(Parm->getFunctionScopeDepth());
131 ID.AddInteger(Parm->getFunctionScopeIndex());
132 return;
133 }
134
135 if (const TemplateTypeParmDecl *TTP =
136 dyn_cast<TemplateTypeParmDecl>(D)) {
137 ID.AddInteger(TTP->getDepth());
138 ID.AddInteger(TTP->getIndex());
139 ID.AddBoolean(TTP->isParameterPack());
140 return;
141 }
142
143 if (const TemplateTemplateParmDecl *TTP =
144 dyn_cast<TemplateTemplateParmDecl>(D)) {
145 ID.AddInteger(TTP->getDepth());
146 ID.AddInteger(TTP->getIndex());
147 ID.AddBoolean(TTP->isParameterPack());
148 return;
149 }
150 }
151
152 ID.AddPointer(D ? D->getCanonicalDecl() : nullptr);
153 }
154
155 void VisitType(QualType T) override {
156 if (Canonical && !T.isNull())
157 T = Context.getCanonicalType(T);
158
159 ID.AddPointer(T.getAsOpaquePtr());
160 }
161
162 void VisitName(DeclarationName Name, bool /*TreatAsDecl*/) override {
163 ID.AddPointer(Name.getAsOpaquePtr());
164 }
165
166 void VisitIdentifierInfo(const IdentifierInfo *II) override {
167 ID.AddPointer(II);
168 }
169
170 void VisitNestedNameSpecifier(NestedNameSpecifier NNS) override {
171 if (Canonical)
172 NNS = NNS.getCanonical();
173 NNS.Profile(ID);
174 }
175
176 void VisitTemplateName(TemplateName Name) override {
177 if (Canonical)
178 Name = Context.getCanonicalTemplateName(Name);
179
180 Name.Profile(ID);
181 }
182 };
183
184 class StmtProfilerWithoutPointers : public StmtProfiler {
185 ODRHash &Hash;
186 public:
187 StmtProfilerWithoutPointers(llvm::FoldingSetNodeID &ID, ODRHash &Hash)
188 : StmtProfiler(ID, /*Canonical=*/false, /*ProfileLambdaExpr=*/false),
189 Hash(Hash) {}
190
191 private:
192 void HandleStmtClass(Stmt::StmtClass SC) override {
193 if (SC == Stmt::UnresolvedLookupExprClass) {
194 // Pretend that the name looked up is a Decl due to how templates
195 // handle some Decl lookups.
196 ID.AddInteger(Stmt::DeclRefExprClass);
197 } else {
198 ID.AddInteger(SC);
199 }
200 }
201
202 void VisitType(QualType T) override {
203 Hash.AddQualType(T);
204 }
205
206 void VisitName(DeclarationName Name, bool TreatAsDecl) override {
207 if (TreatAsDecl) {
208 // A Decl can be null, so each Decl is preceded by a boolean to
209 // store its nullness. Add a boolean here to match.
210 ID.AddBoolean(true);
211 }
212 Hash.AddDeclarationName(Name, TreatAsDecl);
213 }
214 void VisitIdentifierInfo(const IdentifierInfo *II) override {
215 ID.AddBoolean(II);
216 if (II) {
217 Hash.AddIdentifierInfo(II);
218 }
219 }
220 void VisitDecl(const Decl *D) override {
221 ID.AddBoolean(D);
222 if (D) {
223 Hash.AddDecl(D);
224 }
225 }
226 void VisitTemplateName(TemplateName Name) override {
227 Hash.AddTemplateName(Name);
228 }
229 void VisitNestedNameSpecifier(NestedNameSpecifier NNS) override {
230 ID.AddBoolean(bool(NNS));
231 if (NNS)
232 Hash.AddNestedNameSpecifier(NNS);
233 }
234 };
235}
236
237void StmtProfiler::VisitStmt(const Stmt *S) {
238 assert(S && "Requires non-null Stmt pointer");
239
240 VisitStmtNoChildren(S);
241
242 for (const Stmt *SubStmt : S->children()) {
243 if (SubStmt)
244 Visit(SubStmt);
245 else
246 ID.AddInteger(0);
247 }
248}
249
250void StmtProfiler::VisitDeclStmt(const DeclStmt *S) {
251 VisitStmt(S);
252 for (const auto *D : S->decls())
253 VisitDecl(D);
254}
255
256void StmtProfiler::VisitNullStmt(const NullStmt *S) {
257 VisitStmt(S);
258}
259
260void StmtProfiler::VisitCompoundStmt(const CompoundStmt *S) {
261 VisitStmt(S);
262}
263
264void StmtProfiler::VisitCaseStmt(const CaseStmt *S) {
265 VisitStmt(S);
266}
267
268void StmtProfiler::VisitDefaultStmt(const DefaultStmt *S) {
269 VisitStmt(S);
270}
271
272void StmtProfiler::VisitLabelStmt(const LabelStmt *S) {
273 VisitStmt(S);
274 VisitDecl(S->getDecl());
275}
276
277void StmtProfiler::VisitAttributedStmt(const AttributedStmt *S) {
278 VisitStmt(S);
279 // TODO: maybe visit attributes?
280}
281
282void StmtProfiler::VisitIfStmt(const IfStmt *S) {
283 VisitStmt(S);
284 VisitDecl(S->getConditionVariable());
285}
286
287void StmtProfiler::VisitSwitchStmt(const SwitchStmt *S) {
288 VisitStmt(S);
289 VisitDecl(S->getConditionVariable());
290}
291
292void StmtProfiler::VisitWhileStmt(const WhileStmt *S) {
293 VisitStmt(S);
294 VisitDecl(S->getConditionVariable());
295}
296
297void StmtProfiler::VisitDoStmt(const DoStmt *S) {
298 VisitStmt(S);
299}
300
301void StmtProfiler::VisitForStmt(const ForStmt *S) {
302 VisitStmt(S);
303}
304
305void StmtProfiler::VisitGotoStmt(const GotoStmt *S) {
306 VisitStmt(S);
307 VisitDecl(S->getLabel());
308}
309
310void StmtProfiler::VisitIndirectGotoStmt(const IndirectGotoStmt *S) {
311 VisitStmt(S);
312}
313
314void StmtProfiler::VisitContinueStmt(const ContinueStmt *S) {
315 VisitStmt(S);
316}
317
318void StmtProfiler::VisitBreakStmt(const BreakStmt *S) {
319 VisitStmt(S);
320}
321
322void StmtProfiler::VisitReturnStmt(const ReturnStmt *S) {
323 VisitStmt(S);
324}
325
326void StmtProfiler::VisitGCCAsmStmt(const GCCAsmStmt *S) {
327 VisitStmt(S);
328 ID.AddBoolean(S->isVolatile());
329 ID.AddBoolean(S->isSimple());
330 VisitExpr(S->getAsmStringExpr());
331 ID.AddInteger(S->getNumOutputs());
332 for (unsigned I = 0, N = S->getNumOutputs(); I != N; ++I) {
333 ID.AddString(S->getOutputName(I));
334 VisitExpr(S->getOutputConstraintExpr(I));
335 }
336 ID.AddInteger(S->getNumInputs());
337 for (unsigned I = 0, N = S->getNumInputs(); I != N; ++I) {
338 ID.AddString(S->getInputName(I));
339 VisitExpr(S->getInputConstraintExpr(I));
340 }
341 ID.AddInteger(S->getNumClobbers());
342 for (unsigned I = 0, N = S->getNumClobbers(); I != N; ++I)
343 VisitExpr(S->getClobberExpr(I));
344 ID.AddInteger(S->getNumLabels());
345 for (auto *L : S->labels())
346 VisitDecl(L->getLabel());
347}
348
349void StmtProfiler::VisitMSAsmStmt(const MSAsmStmt *S) {
350 // FIXME: Implement MS style inline asm statement profiler.
351 VisitStmt(S);
352}
353
354void StmtProfiler::VisitCXXCatchStmt(const CXXCatchStmt *S) {
355 VisitStmt(S);
356 VisitType(S->getCaughtType());
357}
358
359void StmtProfiler::VisitCXXTryStmt(const CXXTryStmt *S) {
360 VisitStmt(S);
361}
362
363void StmtProfiler::VisitCXXForRangeStmt(const CXXForRangeStmt *S) {
364 VisitStmt(S);
365}
366
367void StmtProfiler::VisitMSDependentExistsStmt(const MSDependentExistsStmt *S) {
368 VisitStmt(S);
369 ID.AddBoolean(S->isIfExists());
370 VisitNestedNameSpecifier(S->getQualifierLoc().getNestedNameSpecifier());
371 VisitName(S->getNameInfo().getName());
372}
373
374void StmtProfiler::VisitSEHTryStmt(const SEHTryStmt *S) {
375 VisitStmt(S);
376}
377
378void StmtProfiler::VisitSEHFinallyStmt(const SEHFinallyStmt *S) {
379 VisitStmt(S);
380}
381
382void StmtProfiler::VisitSEHExceptStmt(const SEHExceptStmt *S) {
383 VisitStmt(S);
384}
385
386void StmtProfiler::VisitSEHLeaveStmt(const SEHLeaveStmt *S) {
387 VisitStmt(S);
388}
389
390void StmtProfiler::VisitCapturedStmt(const CapturedStmt *S) {
391 VisitStmt(S);
392}
393
394void StmtProfiler::VisitSYCLKernelCallStmt(const SYCLKernelCallStmt *S) {
395 VisitStmt(S);
396}
397
398void StmtProfiler::VisitObjCForCollectionStmt(const ObjCForCollectionStmt *S) {
399 VisitStmt(S);
400}
401
402void StmtProfiler::VisitObjCAtCatchStmt(const ObjCAtCatchStmt *S) {
403 VisitStmt(S);
404 ID.AddBoolean(S->hasEllipsis());
405 if (S->getCatchParamDecl())
406 VisitType(S->getCatchParamDecl()->getType());
407}
408
409void StmtProfiler::VisitObjCAtFinallyStmt(const ObjCAtFinallyStmt *S) {
410 VisitStmt(S);
411}
412
413void StmtProfiler::VisitObjCAtTryStmt(const ObjCAtTryStmt *S) {
414 VisitStmt(S);
415}
416
417void
418StmtProfiler::VisitObjCAtSynchronizedStmt(const ObjCAtSynchronizedStmt *S) {
419 VisitStmt(S);
420}
421
422void StmtProfiler::VisitObjCAtThrowStmt(const ObjCAtThrowStmt *S) {
423 VisitStmt(S);
424}
425
426void
427StmtProfiler::VisitObjCAutoreleasePoolStmt(const ObjCAutoreleasePoolStmt *S) {
428 VisitStmt(S);
429}
430
431namespace {
432class OMPClauseProfiler : public ConstOMPClauseVisitor<OMPClauseProfiler> {
433 StmtProfiler *Profiler;
434 /// Process clauses with list of variables.
435 template <typename T>
436 void VisitOMPClauseList(T *Node);
437
438public:
439 OMPClauseProfiler(StmtProfiler *P) : Profiler(P) { }
440#define GEN_CLANG_CLAUSE_CLASS
441#define CLAUSE_CLASS(Enum, Str, Class) void Visit##Class(const Class *C);
442#include "llvm/Frontend/OpenMP/OMP.inc"
443 void VisitOMPClauseWithPreInit(const OMPClauseWithPreInit *C);
444 void VisitOMPClauseWithPostUpdate(const OMPClauseWithPostUpdate *C);
445};
446
447void OMPClauseProfiler::VisitOMPClauseWithPreInit(
448 const OMPClauseWithPreInit *C) {
449 if (auto *S = C->getPreInitStmt())
450 Profiler->VisitStmt(S);
451}
452
453void OMPClauseProfiler::VisitOMPClauseWithPostUpdate(
454 const OMPClauseWithPostUpdate *C) {
455 VisitOMPClauseWithPreInit(C);
456 if (auto *E = C->getPostUpdateExpr())
457 Profiler->VisitStmt(E);
458}
459
460void OMPClauseProfiler::VisitOMPIfClause(const OMPIfClause *C) {
461 VisitOMPClauseWithPreInit(C);
462 if (C->getCondition())
463 Profiler->VisitStmt(C->getCondition());
464}
465
466void OMPClauseProfiler::VisitOMPFinalClause(const OMPFinalClause *C) {
467 VisitOMPClauseWithPreInit(C);
468 if (C->getCondition())
469 Profiler->VisitStmt(C->getCondition());
470}
471
472void OMPClauseProfiler::VisitOMPNumThreadsClause(const OMPNumThreadsClause *C) {
473 VisitOMPClauseWithPreInit(C);
474 if (C->getNumThreads())
475 Profiler->VisitStmt(C->getNumThreads());
476}
477
478void OMPClauseProfiler::VisitOMPAlignClause(const OMPAlignClause *C) {
479 if (C->getAlignment())
480 Profiler->VisitStmt(C->getAlignment());
481}
482
483void OMPClauseProfiler::VisitOMPSafelenClause(const OMPSafelenClause *C) {
484 if (C->getSafelen())
485 Profiler->VisitStmt(C->getSafelen());
486}
487
488void OMPClauseProfiler::VisitOMPSimdlenClause(const OMPSimdlenClause *C) {
489 if (C->getSimdlen())
490 Profiler->VisitStmt(C->getSimdlen());
491}
492
493void OMPClauseProfiler::VisitOMPSizesClause(const OMPSizesClause *C) {
494 for (auto *E : C->getSizesRefs())
495 if (E)
496 Profiler->VisitExpr(E);
497}
498
499void OMPClauseProfiler::VisitOMPPermutationClause(
500 const OMPPermutationClause *C) {
501 for (Expr *E : C->getArgsRefs())
502 if (E)
503 Profiler->VisitExpr(E);
504}
505
506void OMPClauseProfiler::VisitOMPFullClause(const OMPFullClause *C) {}
507
508void OMPClauseProfiler::VisitOMPPartialClause(const OMPPartialClause *C) {
509 if (const Expr *Factor = C->getFactor())
510 Profiler->VisitExpr(Factor);
511}
512
513void OMPClauseProfiler::VisitOMPLoopRangeClause(const OMPLoopRangeClause *C) {
514 if (const Expr *First = C->getFirst())
515 Profiler->VisitExpr(First);
516 if (const Expr *Count = C->getCount())
517 Profiler->VisitExpr(Count);
518}
519
520void OMPClauseProfiler::VisitOMPAllocatorClause(const OMPAllocatorClause *C) {
521 if (C->getAllocator())
522 Profiler->VisitStmt(C->getAllocator());
523}
524
525void OMPClauseProfiler::VisitOMPCollapseClause(const OMPCollapseClause *C) {
526 if (C->getNumForLoops())
527 Profiler->VisitStmt(C->getNumForLoops());
528}
529
530void OMPClauseProfiler::VisitOMPDetachClause(const OMPDetachClause *C) {
531 if (Expr *Evt = C->getEventHandler())
532 Profiler->VisitStmt(Evt);
533}
534
535void OMPClauseProfiler::VisitOMPNovariantsClause(const OMPNovariantsClause *C) {
536 VisitOMPClauseWithPreInit(C);
537 if (C->getCondition())
538 Profiler->VisitStmt(C->getCondition());
539}
540
541void OMPClauseProfiler::VisitOMPNocontextClause(const OMPNocontextClause *C) {
542 VisitOMPClauseWithPreInit(C);
543 if (C->getCondition())
544 Profiler->VisitStmt(C->getCondition());
545}
546
547void OMPClauseProfiler::VisitOMPDefaultClause(const OMPDefaultClause *C) { }
548
549void OMPClauseProfiler::VisitOMPThreadsetClause(const OMPThreadsetClause *C) {}
550
551void OMPClauseProfiler::VisitOMPProcBindClause(const OMPProcBindClause *C) { }
552
553void OMPClauseProfiler::VisitOMPUnifiedAddressClause(
554 const OMPUnifiedAddressClause *C) {}
555
556void OMPClauseProfiler::VisitOMPUnifiedSharedMemoryClause(
557 const OMPUnifiedSharedMemoryClause *C) {}
558
559void OMPClauseProfiler::VisitOMPReverseOffloadClause(
560 const OMPReverseOffloadClause *C) {}
561
562void OMPClauseProfiler::VisitOMPDynamicAllocatorsClause(
563 const OMPDynamicAllocatorsClause *C) {}
564
565void OMPClauseProfiler::VisitOMPAtomicDefaultMemOrderClause(
566 const OMPAtomicDefaultMemOrderClause *C) {}
567
568void OMPClauseProfiler::VisitOMPSelfMapsClause(const OMPSelfMapsClause *C) {}
569
570void OMPClauseProfiler::VisitOMPAtClause(const OMPAtClause *C) {}
571
572void OMPClauseProfiler::VisitOMPSeverityClause(const OMPSeverityClause *C) {}
573
574void OMPClauseProfiler::VisitOMPMessageClause(const OMPMessageClause *C) {
575 if (C->getMessageString())
576 Profiler->VisitStmt(C->getMessageString());
577}
578
579void OMPClauseProfiler::VisitOMPScheduleClause(const OMPScheduleClause *C) {
580 VisitOMPClauseWithPreInit(C);
581 if (auto *S = C->getChunkSize())
582 Profiler->VisitStmt(S);
583}
584
585void OMPClauseProfiler::VisitOMPOrderedClause(const OMPOrderedClause *C) {
586 if (auto *Num = C->getNumForLoops())
587 Profiler->VisitStmt(Num);
588}
589
590void OMPClauseProfiler::VisitOMPNowaitClause(const OMPNowaitClause *C) {
591 if (C->getCondition())
592 Profiler->VisitStmt(C->getCondition());
593}
594
595void OMPClauseProfiler::VisitOMPUntiedClause(const OMPUntiedClause *) {}
596
597void OMPClauseProfiler::VisitOMPMergeableClause(const OMPMergeableClause *) {}
598
599void OMPClauseProfiler::VisitOMPReadClause(const OMPReadClause *) {}
600
601void OMPClauseProfiler::VisitOMPWriteClause(const OMPWriteClause *) {}
602
603void OMPClauseProfiler::VisitOMPUpdateClause(const OMPUpdateClause *) {}
604
605void OMPClauseProfiler::VisitOMPCaptureClause(const OMPCaptureClause *) {}
606
607void OMPClauseProfiler::VisitOMPCompareClause(const OMPCompareClause *) {}
608
609void OMPClauseProfiler::VisitOMPFailClause(const OMPFailClause *) {}
610
611void OMPClauseProfiler::VisitOMPAbsentClause(const OMPAbsentClause *) {}
612
613void OMPClauseProfiler::VisitOMPHoldsClause(const OMPHoldsClause *) {}
614
615void OMPClauseProfiler::VisitOMPContainsClause(const OMPContainsClause *) {}
616
617void OMPClauseProfiler::VisitOMPNoOpenMPClause(const OMPNoOpenMPClause *) {}
618
619void OMPClauseProfiler::VisitOMPNoOpenMPRoutinesClause(
620 const OMPNoOpenMPRoutinesClause *) {}
621
622void OMPClauseProfiler::VisitOMPNoOpenMPConstructsClause(
623 const OMPNoOpenMPConstructsClause *) {}
624
625void OMPClauseProfiler::VisitOMPNoParallelismClause(
626 const OMPNoParallelismClause *) {}
627
628void OMPClauseProfiler::VisitOMPSeqCstClause(const OMPSeqCstClause *) {}
629
630void OMPClauseProfiler::VisitOMPAcqRelClause(const OMPAcqRelClause *) {}
631
632void OMPClauseProfiler::VisitOMPAcquireClause(const OMPAcquireClause *) {}
633
634void OMPClauseProfiler::VisitOMPReleaseClause(const OMPReleaseClause *) {}
635
636void OMPClauseProfiler::VisitOMPRelaxedClause(const OMPRelaxedClause *) {}
637
638void OMPClauseProfiler::VisitOMPWeakClause(const OMPWeakClause *) {}
639
640void OMPClauseProfiler::VisitOMPThreadsClause(const OMPThreadsClause *) {}
641
642void OMPClauseProfiler::VisitOMPSIMDClause(const OMPSIMDClause *) {}
643
644void OMPClauseProfiler::VisitOMPNogroupClause(const OMPNogroupClause *) {}
645
646void OMPClauseProfiler::VisitOMPInitClause(const OMPInitClause *C) {
647 VisitOMPClauseList(C);
648}
649
650void OMPClauseProfiler::VisitOMPUseClause(const OMPUseClause *C) {
651 if (C->getInteropVar())
652 Profiler->VisitStmt(C->getInteropVar());
653}
654
655void OMPClauseProfiler::VisitOMPDestroyClause(const OMPDestroyClause *C) {
656 if (C->getInteropVar())
657 Profiler->VisitStmt(C->getInteropVar());
658}
659
660void OMPClauseProfiler::VisitOMPFilterClause(const OMPFilterClause *C) {
661 VisitOMPClauseWithPreInit(C);
662 if (C->getThreadID())
663 Profiler->VisitStmt(C->getThreadID());
664}
665
666template<typename T>
667void OMPClauseProfiler::VisitOMPClauseList(T *Node) {
668 for (auto *E : Node->varlist()) {
669 if (E)
670 Profiler->VisitStmt(E);
671 }
672}
673
674void OMPClauseProfiler::VisitOMPPrivateClause(const OMPPrivateClause *C) {
675 VisitOMPClauseList(C);
676 for (auto *E : C->private_copies()) {
677 if (E)
678 Profiler->VisitStmt(E);
679 }
680}
681void
682OMPClauseProfiler::VisitOMPFirstprivateClause(const OMPFirstprivateClause *C) {
683 VisitOMPClauseList(C);
684 VisitOMPClauseWithPreInit(C);
685 for (auto *E : C->private_copies()) {
686 if (E)
687 Profiler->VisitStmt(E);
688 }
689 for (auto *E : C->inits()) {
690 if (E)
691 Profiler->VisitStmt(E);
692 }
693}
694void
695OMPClauseProfiler::VisitOMPLastprivateClause(const OMPLastprivateClause *C) {
696 VisitOMPClauseList(C);
697 VisitOMPClauseWithPostUpdate(C);
698 for (auto *E : C->source_exprs()) {
699 if (E)
700 Profiler->VisitStmt(E);
701 }
702 for (auto *E : C->destination_exprs()) {
703 if (E)
704 Profiler->VisitStmt(E);
705 }
706 for (auto *E : C->assignment_ops()) {
707 if (E)
708 Profiler->VisitStmt(E);
709 }
710}
711void OMPClauseProfiler::VisitOMPSharedClause(const OMPSharedClause *C) {
712 VisitOMPClauseList(C);
713}
714void OMPClauseProfiler::VisitOMPReductionClause(
715 const OMPReductionClause *C) {
716 Profiler->VisitNestedNameSpecifier(
717 C->getQualifierLoc().getNestedNameSpecifier());
718 Profiler->VisitName(C->getNameInfo().getName());
719 VisitOMPClauseList(C);
720 VisitOMPClauseWithPostUpdate(C);
721 for (auto *E : C->privates()) {
722 if (E)
723 Profiler->VisitStmt(E);
724 }
725 for (auto *E : C->lhs_exprs()) {
726 if (E)
727 Profiler->VisitStmt(E);
728 }
729 for (auto *E : C->rhs_exprs()) {
730 if (E)
731 Profiler->VisitStmt(E);
732 }
733 for (auto *E : C->reduction_ops()) {
734 if (E)
735 Profiler->VisitStmt(E);
736 }
737 if (C->getModifier() == clang::OMPC_REDUCTION_inscan) {
738 for (auto *E : C->copy_ops()) {
739 if (E)
740 Profiler->VisitStmt(E);
741 }
742 for (auto *E : C->copy_array_temps()) {
743 if (E)
744 Profiler->VisitStmt(E);
745 }
746 for (auto *E : C->copy_array_elems()) {
747 if (E)
748 Profiler->VisitStmt(E);
749 }
750 }
751}
752void OMPClauseProfiler::VisitOMPTaskReductionClause(
753 const OMPTaskReductionClause *C) {
754 Profiler->VisitNestedNameSpecifier(
755 C->getQualifierLoc().getNestedNameSpecifier());
756 Profiler->VisitName(C->getNameInfo().getName());
757 VisitOMPClauseList(C);
758 VisitOMPClauseWithPostUpdate(C);
759 for (auto *E : C->privates()) {
760 if (E)
761 Profiler->VisitStmt(E);
762 }
763 for (auto *E : C->lhs_exprs()) {
764 if (E)
765 Profiler->VisitStmt(E);
766 }
767 for (auto *E : C->rhs_exprs()) {
768 if (E)
769 Profiler->VisitStmt(E);
770 }
771 for (auto *E : C->reduction_ops()) {
772 if (E)
773 Profiler->VisitStmt(E);
774 }
775}
776void OMPClauseProfiler::VisitOMPInReductionClause(
777 const OMPInReductionClause *C) {
778 Profiler->VisitNestedNameSpecifier(
779 C->getQualifierLoc().getNestedNameSpecifier());
780 Profiler->VisitName(C->getNameInfo().getName());
781 VisitOMPClauseList(C);
782 VisitOMPClauseWithPostUpdate(C);
783 for (auto *E : C->privates()) {
784 if (E)
785 Profiler->VisitStmt(E);
786 }
787 for (auto *E : C->lhs_exprs()) {
788 if (E)
789 Profiler->VisitStmt(E);
790 }
791 for (auto *E : C->rhs_exprs()) {
792 if (E)
793 Profiler->VisitStmt(E);
794 }
795 for (auto *E : C->reduction_ops()) {
796 if (E)
797 Profiler->VisitStmt(E);
798 }
799 for (auto *E : C->taskgroup_descriptors()) {
800 if (E)
801 Profiler->VisitStmt(E);
802 }
803}
804void OMPClauseProfiler::VisitOMPLinearClause(const OMPLinearClause *C) {
805 VisitOMPClauseList(C);
806 VisitOMPClauseWithPostUpdate(C);
807 for (auto *E : C->privates()) {
808 if (E)
809 Profiler->VisitStmt(E);
810 }
811 for (auto *E : C->inits()) {
812 if (E)
813 Profiler->VisitStmt(E);
814 }
815 for (auto *E : C->updates()) {
816 if (E)
817 Profiler->VisitStmt(E);
818 }
819 for (auto *E : C->finals()) {
820 if (E)
821 Profiler->VisitStmt(E);
822 }
823 if (C->getStep())
824 Profiler->VisitStmt(C->getStep());
825 if (C->getCalcStep())
826 Profiler->VisitStmt(C->getCalcStep());
827}
828void OMPClauseProfiler::VisitOMPAlignedClause(const OMPAlignedClause *C) {
829 VisitOMPClauseList(C);
830 if (C->getAlignment())
831 Profiler->VisitStmt(C->getAlignment());
832}
833void OMPClauseProfiler::VisitOMPCopyinClause(const OMPCopyinClause *C) {
834 VisitOMPClauseList(C);
835 for (auto *E : C->source_exprs()) {
836 if (E)
837 Profiler->VisitStmt(E);
838 }
839 for (auto *E : C->destination_exprs()) {
840 if (E)
841 Profiler->VisitStmt(E);
842 }
843 for (auto *E : C->assignment_ops()) {
844 if (E)
845 Profiler->VisitStmt(E);
846 }
847}
848void
849OMPClauseProfiler::VisitOMPCopyprivateClause(const OMPCopyprivateClause *C) {
850 VisitOMPClauseList(C);
851 for (auto *E : C->source_exprs()) {
852 if (E)
853 Profiler->VisitStmt(E);
854 }
855 for (auto *E : C->destination_exprs()) {
856 if (E)
857 Profiler->VisitStmt(E);
858 }
859 for (auto *E : C->assignment_ops()) {
860 if (E)
861 Profiler->VisitStmt(E);
862 }
863}
864void OMPClauseProfiler::VisitOMPFlushClause(const OMPFlushClause *C) {
865 VisitOMPClauseList(C);
866}
867void OMPClauseProfiler::VisitOMPDepobjClause(const OMPDepobjClause *C) {
868 if (const Expr *Depobj = C->getDepobj())
869 Profiler->VisitStmt(Depobj);
870}
871void OMPClauseProfiler::VisitOMPDependClause(const OMPDependClause *C) {
872 VisitOMPClauseList(C);
873}
874void OMPClauseProfiler::VisitOMPDeviceClause(const OMPDeviceClause *C) {
875 if (C->getDevice())
876 Profiler->VisitStmt(C->getDevice());
877}
878void OMPClauseProfiler::VisitOMPMapClause(const OMPMapClause *C) {
879 VisitOMPClauseList(C);
880}
881void OMPClauseProfiler::VisitOMPAllocateClause(const OMPAllocateClause *C) {
882 if (Expr *Allocator = C->getAllocator())
883 Profiler->VisitStmt(Allocator);
884 VisitOMPClauseList(C);
885}
886void OMPClauseProfiler::VisitOMPNumTeamsClause(const OMPNumTeamsClause *C) {
887 VisitOMPClauseList(C);
888 VisitOMPClauseWithPreInit(C);
889}
890void OMPClauseProfiler::VisitOMPThreadLimitClause(
891 const OMPThreadLimitClause *C) {
892 VisitOMPClauseList(C);
893 VisitOMPClauseWithPreInit(C);
894}
895void OMPClauseProfiler::VisitOMPPriorityClause(const OMPPriorityClause *C) {
896 VisitOMPClauseWithPreInit(C);
897 if (C->getPriority())
898 Profiler->VisitStmt(C->getPriority());
899}
900void OMPClauseProfiler::VisitOMPGrainsizeClause(const OMPGrainsizeClause *C) {
901 VisitOMPClauseWithPreInit(C);
902 if (C->getGrainsize())
903 Profiler->VisitStmt(C->getGrainsize());
904}
905void OMPClauseProfiler::VisitOMPNumTasksClause(const OMPNumTasksClause *C) {
906 VisitOMPClauseWithPreInit(C);
907 if (C->getNumTasks())
908 Profiler->VisitStmt(C->getNumTasks());
909}
910void OMPClauseProfiler::VisitOMPHintClause(const OMPHintClause *C) {
911 if (C->getHint())
912 Profiler->VisitStmt(C->getHint());
913}
914void OMPClauseProfiler::VisitOMPToClause(const OMPToClause *C) {
915 VisitOMPClauseList(C);
916}
917void OMPClauseProfiler::VisitOMPFromClause(const OMPFromClause *C) {
918 VisitOMPClauseList(C);
919}
920void OMPClauseProfiler::VisitOMPUseDevicePtrClause(
921 const OMPUseDevicePtrClause *C) {
922 VisitOMPClauseList(C);
923}
924void OMPClauseProfiler::VisitOMPUseDeviceAddrClause(
925 const OMPUseDeviceAddrClause *C) {
926 VisitOMPClauseList(C);
927}
928void OMPClauseProfiler::VisitOMPIsDevicePtrClause(
929 const OMPIsDevicePtrClause *C) {
930 VisitOMPClauseList(C);
931}
932void OMPClauseProfiler::VisitOMPHasDeviceAddrClause(
933 const OMPHasDeviceAddrClause *C) {
934 VisitOMPClauseList(C);
935}
936void OMPClauseProfiler::VisitOMPNontemporalClause(
937 const OMPNontemporalClause *C) {
938 VisitOMPClauseList(C);
939 for (auto *E : C->private_refs())
940 Profiler->VisitStmt(E);
941}
942void OMPClauseProfiler::VisitOMPInclusiveClause(const OMPInclusiveClause *C) {
943 VisitOMPClauseList(C);
944}
945void OMPClauseProfiler::VisitOMPExclusiveClause(const OMPExclusiveClause *C) {
946 VisitOMPClauseList(C);
947}
948void OMPClauseProfiler::VisitOMPUsesAllocatorsClause(
949 const OMPUsesAllocatorsClause *C) {
950 for (unsigned I = 0, E = C->getNumberOfAllocators(); I < E; ++I) {
951 OMPUsesAllocatorsClause::Data D = C->getAllocatorData(I);
952 Profiler->VisitStmt(D.Allocator);
953 if (D.AllocatorTraits)
954 Profiler->VisitStmt(D.AllocatorTraits);
955 }
956}
957void OMPClauseProfiler::VisitOMPAffinityClause(const OMPAffinityClause *C) {
958 if (const Expr *Modifier = C->getModifier())
959 Profiler->VisitStmt(Modifier);
960 for (const Expr *E : C->varlist())
961 Profiler->VisitStmt(E);
962}
963void OMPClauseProfiler::VisitOMPOrderClause(const OMPOrderClause *C) {}
964void OMPClauseProfiler::VisitOMPBindClause(const OMPBindClause *C) {}
965void OMPClauseProfiler::VisitOMPXDynCGroupMemClause(
966 const OMPXDynCGroupMemClause *C) {
967 VisitOMPClauseWithPreInit(C);
968 if (Expr *Size = C->getSize())
969 Profiler->VisitStmt(Size);
970}
971void OMPClauseProfiler::VisitOMPDoacrossClause(const OMPDoacrossClause *C) {
972 VisitOMPClauseList(C);
973}
974void OMPClauseProfiler::VisitOMPXAttributeClause(const OMPXAttributeClause *C) {
975}
976void OMPClauseProfiler::VisitOMPXBareClause(const OMPXBareClause *C) {}
977} // namespace
978
979void
980StmtProfiler::VisitOMPExecutableDirective(const OMPExecutableDirective *S) {
981 VisitStmt(S);
982 OMPClauseProfiler P(this);
983 ArrayRef<OMPClause *> Clauses = S->clauses();
984 for (ArrayRef<OMPClause *>::iterator I = Clauses.begin(), E = Clauses.end();
985 I != E; ++I)
986 if (*I)
987 P.Visit(*I);
988}
989
990void StmtProfiler::VisitOMPCanonicalLoop(const OMPCanonicalLoop *L) {
991 VisitStmt(L);
992}
993
994void StmtProfiler::VisitOMPLoopBasedDirective(const OMPLoopBasedDirective *S) {
995 VisitOMPExecutableDirective(S);
996}
997
998void StmtProfiler::VisitOMPLoopDirective(const OMPLoopDirective *S) {
999 VisitOMPLoopBasedDirective(S);
1000}
1001
1002void StmtProfiler::VisitOMPMetaDirective(const OMPMetaDirective *S) {
1003 VisitOMPExecutableDirective(S);
1004}
1005
1006void StmtProfiler::VisitOMPParallelDirective(const OMPParallelDirective *S) {
1007 VisitOMPExecutableDirective(S);
1008}
1009
1010void StmtProfiler::VisitOMPSimdDirective(const OMPSimdDirective *S) {
1011 VisitOMPLoopDirective(S);
1012}
1013
1014void StmtProfiler::VisitOMPCanonicalLoopNestTransformationDirective(
1015 const OMPCanonicalLoopNestTransformationDirective *S) {
1016 VisitOMPLoopBasedDirective(S);
1017}
1018
1019void StmtProfiler::VisitOMPTileDirective(const OMPTileDirective *S) {
1020 VisitOMPCanonicalLoopNestTransformationDirective(S);
1021}
1022
1023void StmtProfiler::VisitOMPStripeDirective(const OMPStripeDirective *S) {
1024 VisitOMPCanonicalLoopNestTransformationDirective(S);
1025}
1026
1027void StmtProfiler::VisitOMPUnrollDirective(const OMPUnrollDirective *S) {
1028 VisitOMPCanonicalLoopNestTransformationDirective(S);
1029}
1030
1031void StmtProfiler::VisitOMPReverseDirective(const OMPReverseDirective *S) {
1032 VisitOMPCanonicalLoopNestTransformationDirective(S);
1033}
1034
1035void StmtProfiler::VisitOMPInterchangeDirective(
1036 const OMPInterchangeDirective *S) {
1037 VisitOMPCanonicalLoopNestTransformationDirective(S);
1038}
1039
1040void StmtProfiler::VisitOMPCanonicalLoopSequenceTransformationDirective(
1041 const OMPCanonicalLoopSequenceTransformationDirective *S) {
1042 VisitOMPExecutableDirective(S);
1043}
1044
1045void StmtProfiler::VisitOMPFuseDirective(const OMPFuseDirective *S) {
1046 VisitOMPCanonicalLoopSequenceTransformationDirective(S);
1047}
1048
1049void StmtProfiler::VisitOMPForDirective(const OMPForDirective *S) {
1050 VisitOMPLoopDirective(S);
1051}
1052
1053void StmtProfiler::VisitOMPForSimdDirective(const OMPForSimdDirective *S) {
1054 VisitOMPLoopDirective(S);
1055}
1056
1057void StmtProfiler::VisitOMPSectionsDirective(const OMPSectionsDirective *S) {
1058 VisitOMPExecutableDirective(S);
1059}
1060
1061void StmtProfiler::VisitOMPSectionDirective(const OMPSectionDirective *S) {
1062 VisitOMPExecutableDirective(S);
1063}
1064
1065void StmtProfiler::VisitOMPScopeDirective(const OMPScopeDirective *S) {
1066 VisitOMPExecutableDirective(S);
1067}
1068
1069void StmtProfiler::VisitOMPSingleDirective(const OMPSingleDirective *S) {
1070 VisitOMPExecutableDirective(S);
1071}
1072
1073void StmtProfiler::VisitOMPMasterDirective(const OMPMasterDirective *S) {
1074 VisitOMPExecutableDirective(S);
1075}
1076
1077void StmtProfiler::VisitOMPCriticalDirective(const OMPCriticalDirective *S) {
1078 VisitOMPExecutableDirective(S);
1079 VisitName(S->getDirectiveName().getName());
1080}
1081
1082void
1083StmtProfiler::VisitOMPParallelForDirective(const OMPParallelForDirective *S) {
1084 VisitOMPLoopDirective(S);
1085}
1086
1087void StmtProfiler::VisitOMPParallelForSimdDirective(
1088 const OMPParallelForSimdDirective *S) {
1089 VisitOMPLoopDirective(S);
1090}
1091
1092void StmtProfiler::VisitOMPParallelMasterDirective(
1093 const OMPParallelMasterDirective *S) {
1094 VisitOMPExecutableDirective(S);
1095}
1096
1097void StmtProfiler::VisitOMPParallelMaskedDirective(
1098 const OMPParallelMaskedDirective *S) {
1099 VisitOMPExecutableDirective(S);
1100}
1101
1102void StmtProfiler::VisitOMPParallelSectionsDirective(
1103 const OMPParallelSectionsDirective *S) {
1104 VisitOMPExecutableDirective(S);
1105}
1106
1107void StmtProfiler::VisitOMPTaskDirective(const OMPTaskDirective *S) {
1108 VisitOMPExecutableDirective(S);
1109}
1110
1111void StmtProfiler::VisitOMPTaskyieldDirective(const OMPTaskyieldDirective *S) {
1112 VisitOMPExecutableDirective(S);
1113}
1114
1115void StmtProfiler::VisitOMPBarrierDirective(const OMPBarrierDirective *S) {
1116 VisitOMPExecutableDirective(S);
1117}
1118
1119void StmtProfiler::VisitOMPTaskwaitDirective(const OMPTaskwaitDirective *S) {
1120 VisitOMPExecutableDirective(S);
1121}
1122
1123void StmtProfiler::VisitOMPAssumeDirective(const OMPAssumeDirective *S) {
1124 VisitOMPExecutableDirective(S);
1125}
1126
1127void StmtProfiler::VisitOMPErrorDirective(const OMPErrorDirective *S) {
1128 VisitOMPExecutableDirective(S);
1129}
1130void StmtProfiler::VisitOMPTaskgroupDirective(const OMPTaskgroupDirective *S) {
1131 VisitOMPExecutableDirective(S);
1132 if (const Expr *E = S->getReductionRef())
1133 VisitStmt(E);
1134}
1135
1136void StmtProfiler::VisitOMPFlushDirective(const OMPFlushDirective *S) {
1137 VisitOMPExecutableDirective(S);
1138}
1139
1140void StmtProfiler::VisitOMPDepobjDirective(const OMPDepobjDirective *S) {
1141 VisitOMPExecutableDirective(S);
1142}
1143
1144void StmtProfiler::VisitOMPScanDirective(const OMPScanDirective *S) {
1145 VisitOMPExecutableDirective(S);
1146}
1147
1148void StmtProfiler::VisitOMPOrderedDirective(const OMPOrderedDirective *S) {
1149 VisitOMPExecutableDirective(S);
1150}
1151
1152void StmtProfiler::VisitOMPAtomicDirective(const OMPAtomicDirective *S) {
1153 VisitOMPExecutableDirective(S);
1154}
1155
1156void StmtProfiler::VisitOMPTargetDirective(const OMPTargetDirective *S) {
1157 VisitOMPExecutableDirective(S);
1158}
1159
1160void StmtProfiler::VisitOMPTargetDataDirective(const OMPTargetDataDirective *S) {
1161 VisitOMPExecutableDirective(S);
1162}
1163
1164void StmtProfiler::VisitOMPTargetEnterDataDirective(
1165 const OMPTargetEnterDataDirective *S) {
1166 VisitOMPExecutableDirective(S);
1167}
1168
1169void StmtProfiler::VisitOMPTargetExitDataDirective(
1170 const OMPTargetExitDataDirective *S) {
1171 VisitOMPExecutableDirective(S);
1172}
1173
1174void StmtProfiler::VisitOMPTargetParallelDirective(
1175 const OMPTargetParallelDirective *S) {
1176 VisitOMPExecutableDirective(S);
1177}
1178
1179void StmtProfiler::VisitOMPTargetParallelForDirective(
1180 const OMPTargetParallelForDirective *S) {
1181 VisitOMPExecutableDirective(S);
1182}
1183
1184void StmtProfiler::VisitOMPTeamsDirective(const OMPTeamsDirective *S) {
1185 VisitOMPExecutableDirective(S);
1186}
1187
1188void StmtProfiler::VisitOMPCancellationPointDirective(
1189 const OMPCancellationPointDirective *S) {
1190 VisitOMPExecutableDirective(S);
1191}
1192
1193void StmtProfiler::VisitOMPCancelDirective(const OMPCancelDirective *S) {
1194 VisitOMPExecutableDirective(S);
1195}
1196
1197void StmtProfiler::VisitOMPTaskLoopDirective(const OMPTaskLoopDirective *S) {
1198 VisitOMPLoopDirective(S);
1199}
1200
1201void StmtProfiler::VisitOMPTaskLoopSimdDirective(
1202 const OMPTaskLoopSimdDirective *S) {
1203 VisitOMPLoopDirective(S);
1204}
1205
1206void StmtProfiler::VisitOMPMasterTaskLoopDirective(
1207 const OMPMasterTaskLoopDirective *S) {
1208 VisitOMPLoopDirective(S);
1209}
1210
1211void StmtProfiler::VisitOMPMaskedTaskLoopDirective(
1212 const OMPMaskedTaskLoopDirective *S) {
1213 VisitOMPLoopDirective(S);
1214}
1215
1216void StmtProfiler::VisitOMPMasterTaskLoopSimdDirective(
1217 const OMPMasterTaskLoopSimdDirective *S) {
1218 VisitOMPLoopDirective(S);
1219}
1220
1221void StmtProfiler::VisitOMPMaskedTaskLoopSimdDirective(
1222 const OMPMaskedTaskLoopSimdDirective *S) {
1223 VisitOMPLoopDirective(S);
1224}
1225
1226void StmtProfiler::VisitOMPParallelMasterTaskLoopDirective(
1227 const OMPParallelMasterTaskLoopDirective *S) {
1228 VisitOMPLoopDirective(S);
1229}
1230
1231void StmtProfiler::VisitOMPParallelMaskedTaskLoopDirective(
1232 const OMPParallelMaskedTaskLoopDirective *S) {
1233 VisitOMPLoopDirective(S);
1234}
1235
1236void StmtProfiler::VisitOMPParallelMasterTaskLoopSimdDirective(
1237 const OMPParallelMasterTaskLoopSimdDirective *S) {
1238 VisitOMPLoopDirective(S);
1239}
1240
1241void StmtProfiler::VisitOMPParallelMaskedTaskLoopSimdDirective(
1242 const OMPParallelMaskedTaskLoopSimdDirective *S) {
1243 VisitOMPLoopDirective(S);
1244}
1245
1246void StmtProfiler::VisitOMPDistributeDirective(
1247 const OMPDistributeDirective *S) {
1248 VisitOMPLoopDirective(S);
1249}
1250
1251void OMPClauseProfiler::VisitOMPDistScheduleClause(
1252 const OMPDistScheduleClause *C) {
1253 VisitOMPClauseWithPreInit(C);
1254 if (auto *S = C->getChunkSize())
1255 Profiler->VisitStmt(S);
1256}
1257
1258void OMPClauseProfiler::VisitOMPDefaultmapClause(const OMPDefaultmapClause *) {}
1259
1260void StmtProfiler::VisitOMPTargetUpdateDirective(
1261 const OMPTargetUpdateDirective *S) {
1262 VisitOMPExecutableDirective(S);
1263}
1264
1265void StmtProfiler::VisitOMPDistributeParallelForDirective(
1266 const OMPDistributeParallelForDirective *S) {
1267 VisitOMPLoopDirective(S);
1268}
1269
1270void StmtProfiler::VisitOMPDistributeParallelForSimdDirective(
1271 const OMPDistributeParallelForSimdDirective *S) {
1272 VisitOMPLoopDirective(S);
1273}
1274
1275void StmtProfiler::VisitOMPDistributeSimdDirective(
1276 const OMPDistributeSimdDirective *S) {
1277 VisitOMPLoopDirective(S);
1278}
1279
1280void StmtProfiler::VisitOMPTargetParallelForSimdDirective(
1281 const OMPTargetParallelForSimdDirective *S) {
1282 VisitOMPLoopDirective(S);
1283}
1284
1285void StmtProfiler::VisitOMPTargetSimdDirective(
1286 const OMPTargetSimdDirective *S) {
1287 VisitOMPLoopDirective(S);
1288}
1289
1290void StmtProfiler::VisitOMPTeamsDistributeDirective(
1291 const OMPTeamsDistributeDirective *S) {
1292 VisitOMPLoopDirective(S);
1293}
1294
1295void StmtProfiler::VisitOMPTeamsDistributeSimdDirective(
1296 const OMPTeamsDistributeSimdDirective *S) {
1297 VisitOMPLoopDirective(S);
1298}
1299
1300void StmtProfiler::VisitOMPTeamsDistributeParallelForSimdDirective(
1301 const OMPTeamsDistributeParallelForSimdDirective *S) {
1302 VisitOMPLoopDirective(S);
1303}
1304
1305void StmtProfiler::VisitOMPTeamsDistributeParallelForDirective(
1306 const OMPTeamsDistributeParallelForDirective *S) {
1307 VisitOMPLoopDirective(S);
1308}
1309
1310void StmtProfiler::VisitOMPTargetTeamsDirective(
1311 const OMPTargetTeamsDirective *S) {
1312 VisitOMPExecutableDirective(S);
1313}
1314
1315void StmtProfiler::VisitOMPTargetTeamsDistributeDirective(
1316 const OMPTargetTeamsDistributeDirective *S) {
1317 VisitOMPLoopDirective(S);
1318}
1319
1320void StmtProfiler::VisitOMPTargetTeamsDistributeParallelForDirective(
1321 const OMPTargetTeamsDistributeParallelForDirective *S) {
1322 VisitOMPLoopDirective(S);
1323}
1324
1325void StmtProfiler::VisitOMPTargetTeamsDistributeParallelForSimdDirective(
1326 const OMPTargetTeamsDistributeParallelForSimdDirective *S) {
1327 VisitOMPLoopDirective(S);
1328}
1329
1330void StmtProfiler::VisitOMPTargetTeamsDistributeSimdDirective(
1331 const OMPTargetTeamsDistributeSimdDirective *S) {
1332 VisitOMPLoopDirective(S);
1333}
1334
1335void StmtProfiler::VisitOMPInteropDirective(const OMPInteropDirective *S) {
1336 VisitOMPExecutableDirective(S);
1337}
1338
1339void StmtProfiler::VisitOMPDispatchDirective(const OMPDispatchDirective *S) {
1340 VisitOMPExecutableDirective(S);
1341}
1342
1343void StmtProfiler::VisitOMPMaskedDirective(const OMPMaskedDirective *S) {
1344 VisitOMPExecutableDirective(S);
1345}
1346
1347void StmtProfiler::VisitOMPGenericLoopDirective(
1348 const OMPGenericLoopDirective *S) {
1349 VisitOMPLoopDirective(S);
1350}
1351
1352void StmtProfiler::VisitOMPTeamsGenericLoopDirective(
1353 const OMPTeamsGenericLoopDirective *S) {
1354 VisitOMPLoopDirective(S);
1355}
1356
1357void StmtProfiler::VisitOMPTargetTeamsGenericLoopDirective(
1358 const OMPTargetTeamsGenericLoopDirective *S) {
1359 VisitOMPLoopDirective(S);
1360}
1361
1362void StmtProfiler::VisitOMPParallelGenericLoopDirective(
1363 const OMPParallelGenericLoopDirective *S) {
1364 VisitOMPLoopDirective(S);
1365}
1366
1367void StmtProfiler::VisitOMPTargetParallelGenericLoopDirective(
1368 const OMPTargetParallelGenericLoopDirective *S) {
1369 VisitOMPLoopDirective(S);
1370}
1371
1372void StmtProfiler::VisitExpr(const Expr *S) {
1373 VisitStmt(S);
1374}
1375
1376void StmtProfiler::VisitConstantExpr(const ConstantExpr *S) {
1377 // Profile exactly as the sub-expression.
1378 Visit(S->getSubExpr());
1379}
1380
1381void StmtProfiler::VisitDeclRefExpr(const DeclRefExpr *S) {
1382 VisitExpr(S);
1383 if (!Canonical)
1384 VisitNestedNameSpecifier(S->getQualifier());
1385 VisitDecl(S->getDecl());
1386 if (!Canonical) {
1387 ID.AddBoolean(S->hasExplicitTemplateArgs());
1388 if (S->hasExplicitTemplateArgs())
1389 VisitTemplateArguments(S->getTemplateArgs(), S->getNumTemplateArgs());
1390 }
1391}
1392
1393void StmtProfiler::VisitSYCLUniqueStableNameExpr(
1394 const SYCLUniqueStableNameExpr *S) {
1395 VisitExpr(S);
1396 VisitType(S->getTypeSourceInfo()->getType());
1397}
1398
1399void StmtProfiler::VisitPredefinedExpr(const PredefinedExpr *S) {
1400 VisitExpr(S);
1401 ID.AddInteger(llvm::to_underlying(S->getIdentKind()));
1402}
1403
1404void StmtProfiler::VisitOpenACCAsteriskSizeExpr(
1405 const OpenACCAsteriskSizeExpr *S) {
1406 VisitExpr(S);
1407}
1408
1409void StmtProfiler::VisitIntegerLiteral(const IntegerLiteral *S) {
1410 VisitExpr(S);
1411 S->getValue().Profile(ID);
1412
1413 QualType T = S->getType();
1414 if (Canonical)
1415 T = T.getCanonicalType();
1416 ID.AddInteger(T->getTypeClass());
1417 if (auto BitIntT = T->getAs<BitIntType>())
1418 BitIntT->Profile(ID);
1419 else
1420 ID.AddInteger(T->castAs<BuiltinType>()->getKind());
1421}
1422
1423void StmtProfiler::VisitFixedPointLiteral(const FixedPointLiteral *S) {
1424 VisitExpr(S);
1425 S->getValue().Profile(ID);
1426 ID.AddInteger(S->getType()->castAs<BuiltinType>()->getKind());
1427}
1428
1429void StmtProfiler::VisitCharacterLiteral(const CharacterLiteral *S) {
1430 VisitExpr(S);
1431 ID.AddInteger(llvm::to_underlying(S->getKind()));
1432 ID.AddInteger(S->getValue());
1433}
1434
1435void StmtProfiler::VisitFloatingLiteral(const FloatingLiteral *S) {
1436 VisitExpr(S);
1437 S->getValue().Profile(ID);
1438 ID.AddBoolean(S->isExact());
1439 ID.AddInteger(S->getType()->castAs<BuiltinType>()->getKind());
1440}
1441
1442void StmtProfiler::VisitImaginaryLiteral(const ImaginaryLiteral *S) {
1443 VisitExpr(S);
1444}
1445
1446void StmtProfiler::VisitStringLiteral(const StringLiteral *S) {
1447 VisitExpr(S);
1448 ID.AddString(S->getBytes());
1449 ID.AddInteger(llvm::to_underlying(S->getKind()));
1450}
1451
1452void StmtProfiler::VisitParenExpr(const ParenExpr *S) {
1453 VisitExpr(S);
1454}
1455
1456void StmtProfiler::VisitParenListExpr(const ParenListExpr *S) {
1457 VisitExpr(S);
1458}
1459
1460void StmtProfiler::VisitUnaryOperator(const UnaryOperator *S) {
1461 VisitExpr(S);
1462 ID.AddInteger(S->getOpcode());
1463}
1464
1465void StmtProfiler::VisitOffsetOfExpr(const OffsetOfExpr *S) {
1466 VisitType(S->getTypeSourceInfo()->getType());
1467 unsigned n = S->getNumComponents();
1468 for (unsigned i = 0; i < n; ++i) {
1469 const OffsetOfNode &ON = S->getComponent(i);
1470 ID.AddInteger(ON.getKind());
1471 switch (ON.getKind()) {
1473 // Expressions handled below.
1474 break;
1475
1477 VisitDecl(ON.getField());
1478 break;
1479
1481 VisitIdentifierInfo(ON.getFieldName());
1482 break;
1483
1484 case OffsetOfNode::Base:
1485 // These nodes are implicit, and therefore don't need profiling.
1486 break;
1487 }
1488 }
1489
1490 VisitExpr(S);
1491}
1492
1493void
1494StmtProfiler::VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *S) {
1495 VisitExpr(S);
1496 ID.AddInteger(S->getKind());
1497 if (S->isArgumentType())
1498 VisitType(S->getArgumentType());
1499}
1500
1501void StmtProfiler::VisitArraySubscriptExpr(const ArraySubscriptExpr *S) {
1502 VisitExpr(S);
1503}
1504
1505void StmtProfiler::VisitMatrixSubscriptExpr(const MatrixSubscriptExpr *S) {
1506 VisitExpr(S);
1507}
1508
1509void StmtProfiler::VisitArraySectionExpr(const ArraySectionExpr *S) {
1510 VisitExpr(S);
1511}
1512
1513void StmtProfiler::VisitOMPArrayShapingExpr(const OMPArrayShapingExpr *S) {
1514 VisitExpr(S);
1515}
1516
1517void StmtProfiler::VisitOMPIteratorExpr(const OMPIteratorExpr *S) {
1518 VisitExpr(S);
1519 for (unsigned I = 0, E = S->numOfIterators(); I < E; ++I)
1520 VisitDecl(S->getIteratorDecl(I));
1521}
1522
1523void StmtProfiler::VisitCallExpr(const CallExpr *S) {
1524 VisitExpr(S);
1525}
1526
1527void StmtProfiler::VisitMemberExpr(const MemberExpr *S) {
1528 VisitExpr(S);
1529 VisitDecl(S->getMemberDecl());
1530 if (!Canonical)
1531 VisitNestedNameSpecifier(S->getQualifier());
1532 ID.AddBoolean(S->isArrow());
1533}
1534
1535void StmtProfiler::VisitCompoundLiteralExpr(const CompoundLiteralExpr *S) {
1536 VisitExpr(S);
1537 ID.AddBoolean(S->isFileScope());
1538}
1539
1540void StmtProfiler::VisitCastExpr(const CastExpr *S) {
1541 VisitExpr(S);
1542}
1543
1544void StmtProfiler::VisitImplicitCastExpr(const ImplicitCastExpr *S) {
1545 VisitCastExpr(S);
1546 ID.AddInteger(S->getValueKind());
1547}
1548
1549void StmtProfiler::VisitExplicitCastExpr(const ExplicitCastExpr *S) {
1550 VisitCastExpr(S);
1551 VisitType(S->getTypeAsWritten());
1552}
1553
1554void StmtProfiler::VisitCStyleCastExpr(const CStyleCastExpr *S) {
1555 VisitExplicitCastExpr(S);
1556}
1557
1558void StmtProfiler::VisitBinaryOperator(const BinaryOperator *S) {
1559 VisitExpr(S);
1560 ID.AddInteger(S->getOpcode());
1561}
1562
1563void
1564StmtProfiler::VisitCompoundAssignOperator(const CompoundAssignOperator *S) {
1565 VisitBinaryOperator(S);
1566}
1567
1568void StmtProfiler::VisitConditionalOperator(const ConditionalOperator *S) {
1569 VisitExpr(S);
1570}
1571
1572void StmtProfiler::VisitBinaryConditionalOperator(
1573 const BinaryConditionalOperator *S) {
1574 VisitExpr(S);
1575}
1576
1577void StmtProfiler::VisitAddrLabelExpr(const AddrLabelExpr *S) {
1578 VisitExpr(S);
1579 VisitDecl(S->getLabel());
1580}
1581
1582void StmtProfiler::VisitStmtExpr(const StmtExpr *S) {
1583 VisitExpr(S);
1584}
1585
1586void StmtProfiler::VisitShuffleVectorExpr(const ShuffleVectorExpr *S) {
1587 VisitExpr(S);
1588}
1589
1590void StmtProfiler::VisitConvertVectorExpr(const ConvertVectorExpr *S) {
1591 VisitExpr(S);
1592}
1593
1594void StmtProfiler::VisitChooseExpr(const ChooseExpr *S) {
1595 VisitExpr(S);
1596}
1597
1598void StmtProfiler::VisitGNUNullExpr(const GNUNullExpr *S) {
1599 VisitExpr(S);
1600}
1601
1602void StmtProfiler::VisitVAArgExpr(const VAArgExpr *S) {
1603 VisitExpr(S);
1604}
1605
1606void StmtProfiler::VisitInitListExpr(const InitListExpr *S) {
1607 if (S->getSyntacticForm()) {
1608 VisitInitListExpr(S->getSyntacticForm());
1609 return;
1610 }
1611
1612 VisitExpr(S);
1613}
1614
1615void StmtProfiler::VisitDesignatedInitExpr(const DesignatedInitExpr *S) {
1616 VisitExpr(S);
1617 ID.AddBoolean(S->usesGNUSyntax());
1618 for (const DesignatedInitExpr::Designator &D : S->designators()) {
1619 if (D.isFieldDesignator()) {
1620 ID.AddInteger(0);
1621 VisitName(D.getFieldName());
1622 continue;
1623 }
1624
1625 if (D.isArrayDesignator()) {
1626 ID.AddInteger(1);
1627 } else {
1628 assert(D.isArrayRangeDesignator());
1629 ID.AddInteger(2);
1630 }
1631 ID.AddInteger(D.getArrayIndex());
1632 }
1633}
1634
1635// Seems that if VisitInitListExpr() only works on the syntactic form of an
1636// InitListExpr, then a DesignatedInitUpdateExpr is not encountered.
1637void StmtProfiler::VisitDesignatedInitUpdateExpr(
1638 const DesignatedInitUpdateExpr *S) {
1639 llvm_unreachable("Unexpected DesignatedInitUpdateExpr in syntactic form of "
1640 "initializer");
1641}
1642
1643void StmtProfiler::VisitArrayInitLoopExpr(const ArrayInitLoopExpr *S) {
1644 VisitExpr(S);
1645}
1646
1647void StmtProfiler::VisitArrayInitIndexExpr(const ArrayInitIndexExpr *S) {
1648 VisitExpr(S);
1649}
1650
1651void StmtProfiler::VisitNoInitExpr(const NoInitExpr *S) {
1652 llvm_unreachable("Unexpected NoInitExpr in syntactic form of initializer");
1653}
1654
1655void StmtProfiler::VisitImplicitValueInitExpr(const ImplicitValueInitExpr *S) {
1656 VisitExpr(S);
1657}
1658
1659void StmtProfiler::VisitExtVectorElementExpr(const ExtVectorElementExpr *S) {
1660 VisitExpr(S);
1661 VisitName(&S->getAccessor());
1662}
1663
1664void StmtProfiler::VisitBlockExpr(const BlockExpr *S) {
1665 VisitExpr(S);
1666 VisitDecl(S->getBlockDecl());
1667}
1668
1669void StmtProfiler::VisitGenericSelectionExpr(const GenericSelectionExpr *S) {
1670 VisitExpr(S);
1672 S->associations()) {
1673 QualType T = Assoc.getType();
1674 if (T.isNull())
1675 ID.AddPointer(nullptr);
1676 else
1677 VisitType(T);
1678 VisitExpr(Assoc.getAssociationExpr());
1679 }
1680}
1681
1682void StmtProfiler::VisitPseudoObjectExpr(const PseudoObjectExpr *S) {
1683 VisitExpr(S);
1685 i = S->semantics_begin(), e = S->semantics_end(); i != e; ++i)
1686 // Normally, we would not profile the source expressions of OVEs.
1687 if (const OpaqueValueExpr *OVE = dyn_cast<OpaqueValueExpr>(*i))
1688 Visit(OVE->getSourceExpr());
1689}
1690
1691void StmtProfiler::VisitAtomicExpr(const AtomicExpr *S) {
1692 VisitExpr(S);
1693 ID.AddInteger(S->getOp());
1694}
1695
1696void StmtProfiler::VisitConceptSpecializationExpr(
1697 const ConceptSpecializationExpr *S) {
1698 VisitExpr(S);
1699 VisitDecl(S->getNamedConcept());
1700 for (const TemplateArgument &Arg : S->getTemplateArguments())
1701 VisitTemplateArgument(Arg);
1702}
1703
1704void StmtProfiler::VisitRequiresExpr(const RequiresExpr *S) {
1705 VisitExpr(S);
1706 ID.AddInteger(S->getLocalParameters().size());
1707 for (ParmVarDecl *LocalParam : S->getLocalParameters())
1708 VisitDecl(LocalParam);
1709 ID.AddInteger(S->getRequirements().size());
1710 for (concepts::Requirement *Req : S->getRequirements()) {
1711 if (auto *TypeReq = dyn_cast<concepts::TypeRequirement>(Req)) {
1712 ID.AddInteger(concepts::Requirement::RK_Type);
1713 ID.AddBoolean(TypeReq->isSubstitutionFailure());
1714 if (!TypeReq->isSubstitutionFailure())
1715 VisitType(TypeReq->getType()->getType());
1716 } else if (auto *ExprReq = dyn_cast<concepts::ExprRequirement>(Req)) {
1718 ID.AddBoolean(ExprReq->isExprSubstitutionFailure());
1719 if (!ExprReq->isExprSubstitutionFailure())
1720 Visit(ExprReq->getExpr());
1721 // C++2a [expr.prim.req.compound]p1 Example:
1722 // [...] The compound-requirement in C1 requires that x++ is a valid
1723 // expression. It is equivalent to the simple-requirement x++; [...]
1724 // We therefore do not profile isSimple() here.
1725 ID.AddBoolean(ExprReq->getNoexceptLoc().isValid());
1726 const concepts::ExprRequirement::ReturnTypeRequirement &RetReq =
1727 ExprReq->getReturnTypeRequirement();
1728 if (RetReq.isEmpty()) {
1729 ID.AddInteger(0);
1730 } else if (RetReq.isTypeConstraint()) {
1731 ID.AddInteger(1);
1733 } else {
1734 assert(RetReq.isSubstitutionFailure());
1735 ID.AddInteger(2);
1736 }
1737 } else {
1738 ID.AddInteger(concepts::Requirement::RK_Nested);
1739 auto *NestedReq = cast<concepts::NestedRequirement>(Req);
1740 ID.AddBoolean(NestedReq->hasInvalidConstraint());
1741 if (!NestedReq->hasInvalidConstraint())
1742 Visit(NestedReq->getConstraintExpr());
1743 }
1744 }
1745}
1746
1748 UnaryOperatorKind &UnaryOp,
1749 BinaryOperatorKind &BinaryOp,
1750 unsigned &NumArgs) {
1751 switch (S->getOperator()) {
1752 case OO_None:
1753 case OO_New:
1754 case OO_Delete:
1755 case OO_Array_New:
1756 case OO_Array_Delete:
1757 case OO_Arrow:
1758 case OO_Conditional:
1760 llvm_unreachable("Invalid operator call kind");
1761
1762 case OO_Plus:
1763 if (NumArgs == 1) {
1764 UnaryOp = UO_Plus;
1765 return Stmt::UnaryOperatorClass;
1766 }
1767
1768 BinaryOp = BO_Add;
1769 return Stmt::BinaryOperatorClass;
1770
1771 case OO_Minus:
1772 if (NumArgs == 1) {
1773 UnaryOp = UO_Minus;
1774 return Stmt::UnaryOperatorClass;
1775 }
1776
1777 BinaryOp = BO_Sub;
1778 return Stmt::BinaryOperatorClass;
1779
1780 case OO_Star:
1781 if (NumArgs == 1) {
1782 UnaryOp = UO_Deref;
1783 return Stmt::UnaryOperatorClass;
1784 }
1785
1786 BinaryOp = BO_Mul;
1787 return Stmt::BinaryOperatorClass;
1788
1789 case OO_Slash:
1790 BinaryOp = BO_Div;
1791 return Stmt::BinaryOperatorClass;
1792
1793 case OO_Percent:
1794 BinaryOp = BO_Rem;
1795 return Stmt::BinaryOperatorClass;
1796
1797 case OO_Caret:
1798 BinaryOp = BO_Xor;
1799 return Stmt::BinaryOperatorClass;
1800
1801 case OO_Amp:
1802 if (NumArgs == 1) {
1803 UnaryOp = UO_AddrOf;
1804 return Stmt::UnaryOperatorClass;
1805 }
1806
1807 BinaryOp = BO_And;
1808 return Stmt::BinaryOperatorClass;
1809
1810 case OO_Pipe:
1811 BinaryOp = BO_Or;
1812 return Stmt::BinaryOperatorClass;
1813
1814 case OO_Tilde:
1815 UnaryOp = UO_Not;
1816 return Stmt::UnaryOperatorClass;
1817
1818 case OO_Exclaim:
1819 UnaryOp = UO_LNot;
1820 return Stmt::UnaryOperatorClass;
1821
1822 case OO_Equal:
1823 BinaryOp = BO_Assign;
1824 return Stmt::BinaryOperatorClass;
1825
1826 case OO_Less:
1827 BinaryOp = BO_LT;
1828 return Stmt::BinaryOperatorClass;
1829
1830 case OO_Greater:
1831 BinaryOp = BO_GT;
1832 return Stmt::BinaryOperatorClass;
1833
1834 case OO_PlusEqual:
1835 BinaryOp = BO_AddAssign;
1836 return Stmt::CompoundAssignOperatorClass;
1837
1838 case OO_MinusEqual:
1839 BinaryOp = BO_SubAssign;
1840 return Stmt::CompoundAssignOperatorClass;
1841
1842 case OO_StarEqual:
1843 BinaryOp = BO_MulAssign;
1844 return Stmt::CompoundAssignOperatorClass;
1845
1846 case OO_SlashEqual:
1847 BinaryOp = BO_DivAssign;
1848 return Stmt::CompoundAssignOperatorClass;
1849
1850 case OO_PercentEqual:
1851 BinaryOp = BO_RemAssign;
1852 return Stmt::CompoundAssignOperatorClass;
1853
1854 case OO_CaretEqual:
1855 BinaryOp = BO_XorAssign;
1856 return Stmt::CompoundAssignOperatorClass;
1857
1858 case OO_AmpEqual:
1859 BinaryOp = BO_AndAssign;
1860 return Stmt::CompoundAssignOperatorClass;
1861
1862 case OO_PipeEqual:
1863 BinaryOp = BO_OrAssign;
1864 return Stmt::CompoundAssignOperatorClass;
1865
1866 case OO_LessLess:
1867 BinaryOp = BO_Shl;
1868 return Stmt::BinaryOperatorClass;
1869
1870 case OO_GreaterGreater:
1871 BinaryOp = BO_Shr;
1872 return Stmt::BinaryOperatorClass;
1873
1874 case OO_LessLessEqual:
1875 BinaryOp = BO_ShlAssign;
1876 return Stmt::CompoundAssignOperatorClass;
1877
1878 case OO_GreaterGreaterEqual:
1879 BinaryOp = BO_ShrAssign;
1880 return Stmt::CompoundAssignOperatorClass;
1881
1882 case OO_EqualEqual:
1883 BinaryOp = BO_EQ;
1884 return Stmt::BinaryOperatorClass;
1885
1886 case OO_ExclaimEqual:
1887 BinaryOp = BO_NE;
1888 return Stmt::BinaryOperatorClass;
1889
1890 case OO_LessEqual:
1891 BinaryOp = BO_LE;
1892 return Stmt::BinaryOperatorClass;
1893
1894 case OO_GreaterEqual:
1895 BinaryOp = BO_GE;
1896 return Stmt::BinaryOperatorClass;
1897
1898 case OO_Spaceship:
1899 BinaryOp = BO_Cmp;
1900 return Stmt::BinaryOperatorClass;
1901
1902 case OO_AmpAmp:
1903 BinaryOp = BO_LAnd;
1904 return Stmt::BinaryOperatorClass;
1905
1906 case OO_PipePipe:
1907 BinaryOp = BO_LOr;
1908 return Stmt::BinaryOperatorClass;
1909
1910 case OO_PlusPlus:
1911 UnaryOp = NumArgs == 1 ? UO_PreInc : UO_PostInc;
1912 NumArgs = 1;
1913 return Stmt::UnaryOperatorClass;
1914
1915 case OO_MinusMinus:
1916 UnaryOp = NumArgs == 1 ? UO_PreDec : UO_PostDec;
1917 NumArgs = 1;
1918 return Stmt::UnaryOperatorClass;
1919
1920 case OO_Comma:
1921 BinaryOp = BO_Comma;
1922 return Stmt::BinaryOperatorClass;
1923
1924 case OO_ArrowStar:
1925 BinaryOp = BO_PtrMemI;
1926 return Stmt::BinaryOperatorClass;
1927
1928 case OO_Subscript:
1929 return Stmt::ArraySubscriptExprClass;
1930
1931 case OO_Call:
1932 return Stmt::CallExprClass;
1933
1934 case OO_Coawait:
1935 UnaryOp = UO_Coawait;
1936 return Stmt::UnaryOperatorClass;
1937 }
1938
1939 llvm_unreachable("Invalid overloaded operator expression");
1940}
1941
1942#if defined(_MSC_VER) && !defined(__clang__)
1943#if _MSC_VER == 1911
1944// Work around https://developercommunity.visualstudio.com/content/problem/84002/clang-cl-when-built-with-vc-2017-crashes-cause-vc.html
1945// MSVC 2017 update 3 miscompiles this function, and a clang built with it
1946// will crash in stage 2 of a bootstrap build.
1947#pragma optimize("", off)
1948#endif
1949#endif
1950
1951void StmtProfiler::VisitCXXOperatorCallExpr(const CXXOperatorCallExpr *S) {
1952 if (S->isTypeDependent()) {
1953 // Type-dependent operator calls are profiled like their underlying
1954 // syntactic operator.
1955 //
1956 // An operator call to operator-> is always implicit, so just skip it. The
1957 // enclosing MemberExpr will profile the actual member access.
1958 if (S->getOperator() == OO_Arrow)
1959 return Visit(S->getArg(0));
1960
1961 UnaryOperatorKind UnaryOp = UO_Extension;
1962 BinaryOperatorKind BinaryOp = BO_Comma;
1963 unsigned NumArgs = S->getNumArgs();
1964 Stmt::StmtClass SC = DecodeOperatorCall(S, UnaryOp, BinaryOp, NumArgs);
1965
1966 ID.AddInteger(SC);
1967 for (unsigned I = 0; I != NumArgs; ++I)
1968 Visit(S->getArg(I));
1969 if (SC == Stmt::UnaryOperatorClass)
1970 ID.AddInteger(UnaryOp);
1971 else if (SC == Stmt::BinaryOperatorClass ||
1972 SC == Stmt::CompoundAssignOperatorClass)
1973 ID.AddInteger(BinaryOp);
1974 else
1975 assert(SC == Stmt::ArraySubscriptExprClass || SC == Stmt::CallExprClass);
1976
1977 return;
1978 }
1979
1980 VisitCallExpr(S);
1981 ID.AddInteger(S->getOperator());
1982}
1983
1984void StmtProfiler::VisitCXXRewrittenBinaryOperator(
1985 const CXXRewrittenBinaryOperator *S) {
1986 // If a rewritten operator were ever to be type-dependent, we should profile
1987 // it following its syntactic operator.
1988 assert(!S->isTypeDependent() &&
1989 "resolved rewritten operator should never be type-dependent");
1990 ID.AddBoolean(S->isReversed());
1991 VisitExpr(S->getSemanticForm());
1992}
1993
1994#if defined(_MSC_VER) && !defined(__clang__)
1995#if _MSC_VER == 1911
1996#pragma optimize("", on)
1997#endif
1998#endif
1999
2000void StmtProfiler::VisitCXXMemberCallExpr(const CXXMemberCallExpr *S) {
2001 VisitCallExpr(S);
2002}
2003
2004void StmtProfiler::VisitCUDAKernelCallExpr(const CUDAKernelCallExpr *S) {
2005 VisitCallExpr(S);
2006}
2007
2008void StmtProfiler::VisitAsTypeExpr(const AsTypeExpr *S) {
2009 VisitExpr(S);
2010}
2011
2012void StmtProfiler::VisitCXXNamedCastExpr(const CXXNamedCastExpr *S) {
2013 VisitExplicitCastExpr(S);
2014}
2015
2016void StmtProfiler::VisitCXXStaticCastExpr(const CXXStaticCastExpr *S) {
2017 VisitCXXNamedCastExpr(S);
2018}
2019
2020void StmtProfiler::VisitCXXDynamicCastExpr(const CXXDynamicCastExpr *S) {
2021 VisitCXXNamedCastExpr(S);
2022}
2023
2024void
2025StmtProfiler::VisitCXXReinterpretCastExpr(const CXXReinterpretCastExpr *S) {
2026 VisitCXXNamedCastExpr(S);
2027}
2028
2029void StmtProfiler::VisitCXXConstCastExpr(const CXXConstCastExpr *S) {
2030 VisitCXXNamedCastExpr(S);
2031}
2032
2033void StmtProfiler::VisitBuiltinBitCastExpr(const BuiltinBitCastExpr *S) {
2034 VisitExpr(S);
2035 VisitType(S->getTypeInfoAsWritten()->getType());
2036}
2037
2038void StmtProfiler::VisitCXXAddrspaceCastExpr(const CXXAddrspaceCastExpr *S) {
2039 VisitCXXNamedCastExpr(S);
2040}
2041
2042void StmtProfiler::VisitUserDefinedLiteral(const UserDefinedLiteral *S) {
2043 VisitCallExpr(S);
2044}
2045
2046void StmtProfiler::VisitCXXBoolLiteralExpr(const CXXBoolLiteralExpr *S) {
2047 VisitExpr(S);
2048 ID.AddBoolean(S->getValue());
2049}
2050
2051void StmtProfiler::VisitCXXNullPtrLiteralExpr(const CXXNullPtrLiteralExpr *S) {
2052 VisitExpr(S);
2053}
2054
2055void StmtProfiler::VisitCXXStdInitializerListExpr(
2056 const CXXStdInitializerListExpr *S) {
2057 VisitExpr(S);
2058}
2059
2060void StmtProfiler::VisitCXXTypeidExpr(const CXXTypeidExpr *S) {
2061 VisitExpr(S);
2062 if (S->isTypeOperand())
2063 VisitType(S->getTypeOperandSourceInfo()->getType());
2064}
2065
2066void StmtProfiler::VisitCXXUuidofExpr(const CXXUuidofExpr *S) {
2067 VisitExpr(S);
2068 if (S->isTypeOperand())
2069 VisitType(S->getTypeOperandSourceInfo()->getType());
2070}
2071
2072void StmtProfiler::VisitMSPropertyRefExpr(const MSPropertyRefExpr *S) {
2073 VisitExpr(S);
2074 VisitDecl(S->getPropertyDecl());
2075}
2076
2077void StmtProfiler::VisitMSPropertySubscriptExpr(
2078 const MSPropertySubscriptExpr *S) {
2079 VisitExpr(S);
2080}
2081
2082void StmtProfiler::VisitCXXThisExpr(const CXXThisExpr *S) {
2083 VisitExpr(S);
2084 ID.AddBoolean(S->isImplicit());
2086}
2087
2088void StmtProfiler::VisitCXXThrowExpr(const CXXThrowExpr *S) {
2089 VisitExpr(S);
2090}
2091
2092void StmtProfiler::VisitCXXDefaultArgExpr(const CXXDefaultArgExpr *S) {
2093 VisitExpr(S);
2094 VisitDecl(S->getParam());
2095}
2096
2097void StmtProfiler::VisitCXXDefaultInitExpr(const CXXDefaultInitExpr *S) {
2098 VisitExpr(S);
2099 VisitDecl(S->getField());
2100}
2101
2102void StmtProfiler::VisitCXXBindTemporaryExpr(const CXXBindTemporaryExpr *S) {
2103 VisitExpr(S);
2104 VisitDecl(
2105 const_cast<CXXDestructorDecl *>(S->getTemporary()->getDestructor()));
2106}
2107
2108void StmtProfiler::VisitCXXConstructExpr(const CXXConstructExpr *S) {
2109 VisitExpr(S);
2110 VisitDecl(S->getConstructor());
2111 ID.AddBoolean(S->isElidable());
2112}
2113
2114void StmtProfiler::VisitCXXInheritedCtorInitExpr(
2115 const CXXInheritedCtorInitExpr *S) {
2116 VisitExpr(S);
2117 VisitDecl(S->getConstructor());
2118}
2119
2120void StmtProfiler::VisitCXXFunctionalCastExpr(const CXXFunctionalCastExpr *S) {
2121 VisitExplicitCastExpr(S);
2122}
2123
2124void
2125StmtProfiler::VisitCXXTemporaryObjectExpr(const CXXTemporaryObjectExpr *S) {
2126 VisitCXXConstructExpr(S);
2127}
2128
2129void
2130StmtProfiler::VisitLambdaExpr(const LambdaExpr *S) {
2131 if (!ProfileLambdaExpr) {
2132 // Do not recursively visit the children of this expression. Profiling the
2133 // body would result in unnecessary work, and is not safe to do during
2134 // deserialization.
2135 VisitStmtNoChildren(S);
2136
2137 // C++20 [temp.over.link]p5:
2138 // Two lambda-expressions are never considered equivalent.
2139 VisitDecl(S->getLambdaClass());
2140
2141 return;
2142 }
2143
2144 CXXRecordDecl *Lambda = S->getLambdaClass();
2145 for (const auto &Capture : Lambda->captures()) {
2146 ID.AddInteger(Capture.getCaptureKind());
2147 if (Capture.capturesVariable())
2148 VisitDecl(Capture.getCapturedVar());
2149 }
2150
2151 // Profiling the body of the lambda may be dangerous during deserialization.
2152 // So we'd like only to profile the signature here.
2153 ODRHash Hasher;
2154 // FIXME: We can't get the operator call easily by
2155 // `CXXRecordDecl::getLambdaCallOperator()` if we're in deserialization.
2156 // So we have to do something raw here.
2157 for (auto *SubDecl : Lambda->decls()) {
2158 FunctionDecl *Call = nullptr;
2159 if (auto *FTD = dyn_cast<FunctionTemplateDecl>(SubDecl))
2160 Call = FTD->getTemplatedDecl();
2161 else if (auto *FD = dyn_cast<FunctionDecl>(SubDecl))
2162 Call = FD;
2163
2164 if (!Call)
2165 continue;
2166
2167 Hasher.AddFunctionDecl(Call, /*SkipBody=*/true);
2168 }
2169 ID.AddInteger(Hasher.CalculateHash());
2170}
2171
2172void
2173StmtProfiler::VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *S) {
2174 VisitExpr(S);
2175}
2176
2177void StmtProfiler::VisitCXXDeleteExpr(const CXXDeleteExpr *S) {
2178 VisitExpr(S);
2179 ID.AddBoolean(S->isGlobalDelete());
2180 ID.AddBoolean(S->isArrayForm());
2181 VisitDecl(S->getOperatorDelete());
2182}
2183
2184void StmtProfiler::VisitCXXNewExpr(const CXXNewExpr *S) {
2185 VisitExpr(S);
2186 VisitType(S->getAllocatedType());
2187 VisitDecl(S->getOperatorNew());
2188 VisitDecl(S->getOperatorDelete());
2189 ID.AddBoolean(S->isArray());
2190 ID.AddInteger(S->getNumPlacementArgs());
2191 ID.AddBoolean(S->isGlobalNew());
2192 ID.AddBoolean(S->isParenTypeId());
2193 ID.AddInteger(llvm::to_underlying(S->getInitializationStyle()));
2194}
2195
2196void
2197StmtProfiler::VisitCXXPseudoDestructorExpr(const CXXPseudoDestructorExpr *S) {
2198 VisitExpr(S);
2199 ID.AddBoolean(S->isArrow());
2200 VisitNestedNameSpecifier(S->getQualifier());
2201 ID.AddBoolean(S->getScopeTypeInfo() != nullptr);
2202 if (S->getScopeTypeInfo())
2203 VisitType(S->getScopeTypeInfo()->getType());
2204 ID.AddBoolean(S->getDestroyedTypeInfo() != nullptr);
2205 if (S->getDestroyedTypeInfo())
2206 VisitType(S->getDestroyedType());
2207 else
2208 VisitIdentifierInfo(S->getDestroyedTypeIdentifier());
2209}
2210
2211void StmtProfiler::VisitOverloadExpr(const OverloadExpr *S) {
2212 VisitExpr(S);
2213 bool DescribingDependentVarTemplate =
2214 S->getNumDecls() == 1 && isa<VarTemplateDecl>(*S->decls_begin());
2215 if (DescribingDependentVarTemplate) {
2216 VisitDecl(*S->decls_begin());
2217 } else {
2218 VisitNestedNameSpecifier(S->getQualifier());
2219 VisitName(S->getName(), /*TreatAsDecl*/ true);
2220 }
2221 ID.AddBoolean(S->hasExplicitTemplateArgs());
2222 if (S->hasExplicitTemplateArgs())
2223 VisitTemplateArguments(S->getTemplateArgs(), S->getNumTemplateArgs());
2224}
2225
2226void
2227StmtProfiler::VisitUnresolvedLookupExpr(const UnresolvedLookupExpr *S) {
2228 VisitOverloadExpr(S);
2229}
2230
2231void StmtProfiler::VisitTypeTraitExpr(const TypeTraitExpr *S) {
2232 VisitExpr(S);
2233 ID.AddInteger(S->getTrait());
2234 ID.AddInteger(S->getNumArgs());
2235 for (unsigned I = 0, N = S->getNumArgs(); I != N; ++I)
2236 VisitType(S->getArg(I)->getType());
2237}
2238
2239void StmtProfiler::VisitArrayTypeTraitExpr(const ArrayTypeTraitExpr *S) {
2240 VisitExpr(S);
2241 ID.AddInteger(S->getTrait());
2242 VisitType(S->getQueriedType());
2243}
2244
2245void StmtProfiler::VisitExpressionTraitExpr(const ExpressionTraitExpr *S) {
2246 VisitExpr(S);
2247 ID.AddInteger(S->getTrait());
2248 VisitExpr(S->getQueriedExpression());
2249}
2250
2251void StmtProfiler::VisitDependentScopeDeclRefExpr(
2252 const DependentScopeDeclRefExpr *S) {
2253 VisitExpr(S);
2254 VisitName(S->getDeclName());
2255 VisitNestedNameSpecifier(S->getQualifier());
2256 ID.AddBoolean(S->hasExplicitTemplateArgs());
2257 if (S->hasExplicitTemplateArgs())
2258 VisitTemplateArguments(S->getTemplateArgs(), S->getNumTemplateArgs());
2259}
2260
2261void StmtProfiler::VisitExprWithCleanups(const ExprWithCleanups *S) {
2262 VisitExpr(S);
2263}
2264
2265void StmtProfiler::VisitCXXUnresolvedConstructExpr(
2266 const CXXUnresolvedConstructExpr *S) {
2267 VisitExpr(S);
2268 VisitType(S->getTypeAsWritten());
2269 ID.AddInteger(S->isListInitialization());
2270}
2271
2272void StmtProfiler::VisitCXXDependentScopeMemberExpr(
2273 const CXXDependentScopeMemberExpr *S) {
2274 ID.AddBoolean(S->isImplicitAccess());
2275 if (!S->isImplicitAccess()) {
2276 VisitExpr(S);
2277 ID.AddBoolean(S->isArrow());
2278 }
2279 VisitNestedNameSpecifier(S->getQualifier());
2280 VisitName(S->getMember());
2281 ID.AddBoolean(S->hasExplicitTemplateArgs());
2282 if (S->hasExplicitTemplateArgs())
2283 VisitTemplateArguments(S->getTemplateArgs(), S->getNumTemplateArgs());
2284}
2285
2286void StmtProfiler::VisitUnresolvedMemberExpr(const UnresolvedMemberExpr *S) {
2287 ID.AddBoolean(S->isImplicitAccess());
2288 if (!S->isImplicitAccess()) {
2289 VisitExpr(S);
2290 ID.AddBoolean(S->isArrow());
2291 }
2292 VisitNestedNameSpecifier(S->getQualifier());
2293 VisitName(S->getMemberName());
2294 ID.AddBoolean(S->hasExplicitTemplateArgs());
2295 if (S->hasExplicitTemplateArgs())
2296 VisitTemplateArguments(S->getTemplateArgs(), S->getNumTemplateArgs());
2297}
2298
2299void StmtProfiler::VisitCXXNoexceptExpr(const CXXNoexceptExpr *S) {
2300 VisitExpr(S);
2301}
2302
2303void StmtProfiler::VisitPackExpansionExpr(const PackExpansionExpr *S) {
2304 VisitExpr(S);
2305}
2306
2307void StmtProfiler::VisitSizeOfPackExpr(const SizeOfPackExpr *S) {
2308 VisitExpr(S);
2309 if (S->isPartiallySubstituted()) {
2310 auto Args = S->getPartialArguments();
2311 ID.AddInteger(Args.size());
2312 for (const auto &TA : Args)
2313 VisitTemplateArgument(TA);
2314 } else {
2315 VisitDecl(S->getPack());
2316 ID.AddInteger(0);
2317 }
2318}
2319
2320void StmtProfiler::VisitPackIndexingExpr(const PackIndexingExpr *E) {
2321 VisitExpr(E->getIndexExpr());
2322
2323 if (E->expandsToEmptyPack() || E->getExpressions().size() != 0) {
2324 ID.AddInteger(E->getExpressions().size());
2325 for (const Expr *Sub : E->getExpressions())
2326 Visit(Sub);
2327 } else {
2328 VisitExpr(E->getPackIdExpression());
2329 }
2330}
2331
2332void StmtProfiler::VisitSubstNonTypeTemplateParmPackExpr(
2333 const SubstNonTypeTemplateParmPackExpr *S) {
2334 VisitExpr(S);
2335 VisitDecl(S->getParameterPack());
2336 VisitTemplateArgument(S->getArgumentPack());
2337}
2338
2339void StmtProfiler::VisitSubstNonTypeTemplateParmExpr(
2340 const SubstNonTypeTemplateParmExpr *E) {
2341 // Profile exactly as the replacement expression.
2342 Visit(E->getReplacement());
2343}
2344
2345void StmtProfiler::VisitFunctionParmPackExpr(const FunctionParmPackExpr *S) {
2346 VisitExpr(S);
2347 VisitDecl(S->getParameterPack());
2348 ID.AddInteger(S->getNumExpansions());
2349 for (FunctionParmPackExpr::iterator I = S->begin(), E = S->end(); I != E; ++I)
2350 VisitDecl(*I);
2351}
2352
2353void StmtProfiler::VisitMaterializeTemporaryExpr(
2354 const MaterializeTemporaryExpr *S) {
2355 VisitExpr(S);
2356}
2357
2358void StmtProfiler::VisitCXXFoldExpr(const CXXFoldExpr *S) {
2359 VisitExpr(S);
2360 ID.AddInteger(S->getOperator());
2361}
2362
2363void StmtProfiler::VisitCXXParenListInitExpr(const CXXParenListInitExpr *S) {
2364 VisitExpr(S);
2365}
2366
2367void StmtProfiler::VisitCoroutineBodyStmt(const CoroutineBodyStmt *S) {
2368 VisitStmt(S);
2369}
2370
2371void StmtProfiler::VisitCoreturnStmt(const CoreturnStmt *S) {
2372 VisitStmt(S);
2373}
2374
2375void StmtProfiler::VisitCoawaitExpr(const CoawaitExpr *S) {
2376 VisitExpr(S);
2377}
2378
2379void StmtProfiler::VisitDependentCoawaitExpr(const DependentCoawaitExpr *S) {
2380 VisitExpr(S);
2381}
2382
2383void StmtProfiler::VisitCoyieldExpr(const CoyieldExpr *S) {
2384 VisitExpr(S);
2385}
2386
2387void StmtProfiler::VisitOpaqueValueExpr(const OpaqueValueExpr *E) {
2388 VisitExpr(E);
2389}
2390
2391void StmtProfiler::VisitSourceLocExpr(const SourceLocExpr *E) {
2392 VisitExpr(E);
2393}
2394
2395void StmtProfiler::VisitEmbedExpr(const EmbedExpr *E) { VisitExpr(E); }
2396
2397void StmtProfiler::VisitRecoveryExpr(const RecoveryExpr *E) { VisitExpr(E); }
2398
2399void StmtProfiler::VisitObjCStringLiteral(const ObjCStringLiteral *S) {
2400 VisitExpr(S);
2401}
2402
2403void StmtProfiler::VisitObjCBoxedExpr(const ObjCBoxedExpr *E) {
2404 VisitExpr(E);
2405}
2406
2407void StmtProfiler::VisitObjCArrayLiteral(const ObjCArrayLiteral *E) {
2408 VisitExpr(E);
2409}
2410
2411void StmtProfiler::VisitObjCDictionaryLiteral(const ObjCDictionaryLiteral *E) {
2412 VisitExpr(E);
2413}
2414
2415void StmtProfiler::VisitObjCEncodeExpr(const ObjCEncodeExpr *S) {
2416 VisitExpr(S);
2417 VisitType(S->getEncodedType());
2418}
2419
2420void StmtProfiler::VisitObjCSelectorExpr(const ObjCSelectorExpr *S) {
2421 VisitExpr(S);
2422 VisitName(S->getSelector());
2423}
2424
2425void StmtProfiler::VisitObjCProtocolExpr(const ObjCProtocolExpr *S) {
2426 VisitExpr(S);
2427 VisitDecl(S->getProtocol());
2428}
2429
2430void StmtProfiler::VisitObjCIvarRefExpr(const ObjCIvarRefExpr *S) {
2431 VisitExpr(S);
2432 VisitDecl(S->getDecl());
2433 ID.AddBoolean(S->isArrow());
2434 ID.AddBoolean(S->isFreeIvar());
2435}
2436
2437void StmtProfiler::VisitObjCPropertyRefExpr(const ObjCPropertyRefExpr *S) {
2438 VisitExpr(S);
2439 if (S->isImplicitProperty()) {
2440 VisitDecl(S->getImplicitPropertyGetter());
2441 VisitDecl(S->getImplicitPropertySetter());
2442 } else {
2443 VisitDecl(S->getExplicitProperty());
2444 }
2445 if (S->isSuperReceiver()) {
2446 ID.AddBoolean(S->isSuperReceiver());
2447 VisitType(S->getSuperReceiverType());
2448 }
2449}
2450
2451void StmtProfiler::VisitObjCSubscriptRefExpr(const ObjCSubscriptRefExpr *S) {
2452 VisitExpr(S);
2453 VisitDecl(S->getAtIndexMethodDecl());
2454 VisitDecl(S->setAtIndexMethodDecl());
2455}
2456
2457void StmtProfiler::VisitObjCMessageExpr(const ObjCMessageExpr *S) {
2458 VisitExpr(S);
2459 VisitName(S->getSelector());
2460 VisitDecl(S->getMethodDecl());
2461}
2462
2463void StmtProfiler::VisitObjCIsaExpr(const ObjCIsaExpr *S) {
2464 VisitExpr(S);
2465 ID.AddBoolean(S->isArrow());
2466}
2467
2468void StmtProfiler::VisitObjCBoolLiteralExpr(const ObjCBoolLiteralExpr *S) {
2469 VisitExpr(S);
2470 ID.AddBoolean(S->getValue());
2471}
2472
2473void StmtProfiler::VisitObjCIndirectCopyRestoreExpr(
2474 const ObjCIndirectCopyRestoreExpr *S) {
2475 VisitExpr(S);
2476 ID.AddBoolean(S->shouldCopy());
2477}
2478
2479void StmtProfiler::VisitObjCBridgedCastExpr(const ObjCBridgedCastExpr *S) {
2480 VisitExplicitCastExpr(S);
2481 ID.AddBoolean(S->getBridgeKind());
2482}
2483
2484void StmtProfiler::VisitObjCAvailabilityCheckExpr(
2485 const ObjCAvailabilityCheckExpr *S) {
2486 VisitExpr(S);
2487}
2488
2489void StmtProfiler::VisitTemplateArguments(const TemplateArgumentLoc *Args,
2490 unsigned NumArgs) {
2491 ID.AddInteger(NumArgs);
2492 for (unsigned I = 0; I != NumArgs; ++I)
2493 VisitTemplateArgument(Args[I].getArgument());
2494}
2495
2496void StmtProfiler::VisitTemplateArgument(const TemplateArgument &Arg) {
2497 // Mostly repetitive with TemplateArgument::Profile!
2498 ID.AddInteger(Arg.getKind());
2499 switch (Arg.getKind()) {
2501 break;
2502
2504 VisitType(Arg.getAsType());
2505 break;
2506
2509 VisitTemplateName(Arg.getAsTemplateOrTemplatePattern());
2510 break;
2511
2513 VisitType(Arg.getParamTypeForDecl());
2514 // FIXME: Do we need to recursively decompose template parameter objects?
2515 VisitDecl(Arg.getAsDecl());
2516 break;
2517
2519 VisitType(Arg.getNullPtrType());
2520 break;
2521
2523 VisitType(Arg.getIntegralType());
2524 Arg.getAsIntegral().Profile(ID);
2525 break;
2526
2528 VisitType(Arg.getStructuralValueType());
2529 // FIXME: Do we need to recursively decompose this ourselves?
2530 Arg.getAsStructuralValue().Profile(ID);
2531 break;
2532
2534 Visit(Arg.getAsExpr());
2535 break;
2536
2538 for (const auto &P : Arg.pack_elements())
2539 VisitTemplateArgument(P);
2540 break;
2541 }
2542}
2543
2544namespace {
2545class OpenACCClauseProfiler
2546 : public OpenACCClauseVisitor<OpenACCClauseProfiler> {
2547 StmtProfiler &Profiler;
2548
2549public:
2550 OpenACCClauseProfiler(StmtProfiler &P) : Profiler(P) {}
2551
2552 void VisitOpenACCClauseList(ArrayRef<const OpenACCClause *> Clauses) {
2553 for (const OpenACCClause *Clause : Clauses) {
2554 // TODO OpenACC: When we have clauses with expressions, we should
2555 // profile them too.
2556 Visit(Clause);
2557 }
2558 }
2559
2560 void VisitClauseWithVarList(const OpenACCClauseWithVarList &Clause) {
2561 for (auto *E : Clause.getVarList())
2562 Profiler.VisitStmt(E);
2563 }
2564
2565#define VISIT_CLAUSE(CLAUSE_NAME) \
2566 void Visit##CLAUSE_NAME##Clause(const OpenACC##CLAUSE_NAME##Clause &Clause);
2567
2568#include "clang/Basic/OpenACCClauses.def"
2569};
2570
2571/// Nothing to do here, there are no sub-statements.
2572void OpenACCClauseProfiler::VisitDefaultClause(
2573 const OpenACCDefaultClause &Clause) {}
2574
2575void OpenACCClauseProfiler::VisitIfClause(const OpenACCIfClause &Clause) {
2576 assert(Clause.hasConditionExpr() &&
2577 "if clause requires a valid condition expr");
2578 Profiler.VisitStmt(Clause.getConditionExpr());
2579}
2580
2581void OpenACCClauseProfiler::VisitCopyClause(const OpenACCCopyClause &Clause) {
2582 VisitClauseWithVarList(Clause);
2583}
2584
2585void OpenACCClauseProfiler::VisitLinkClause(const OpenACCLinkClause &Clause) {
2586 VisitClauseWithVarList(Clause);
2587}
2588
2589void OpenACCClauseProfiler::VisitDeviceResidentClause(
2590 const OpenACCDeviceResidentClause &Clause) {
2591 VisitClauseWithVarList(Clause);
2592}
2593
2594void OpenACCClauseProfiler::VisitCopyInClause(
2595 const OpenACCCopyInClause &Clause) {
2596 VisitClauseWithVarList(Clause);
2597}
2598
2599void OpenACCClauseProfiler::VisitCopyOutClause(
2600 const OpenACCCopyOutClause &Clause) {
2601 VisitClauseWithVarList(Clause);
2602}
2603
2604void OpenACCClauseProfiler::VisitCreateClause(
2605 const OpenACCCreateClause &Clause) {
2606 VisitClauseWithVarList(Clause);
2607}
2608
2609void OpenACCClauseProfiler::VisitHostClause(const OpenACCHostClause &Clause) {
2610 VisitClauseWithVarList(Clause);
2611}
2612
2613void OpenACCClauseProfiler::VisitDeviceClause(
2614 const OpenACCDeviceClause &Clause) {
2615 VisitClauseWithVarList(Clause);
2616}
2617
2618void OpenACCClauseProfiler::VisitSelfClause(const OpenACCSelfClause &Clause) {
2619 if (Clause.isConditionExprClause()) {
2620 if (Clause.hasConditionExpr())
2621 Profiler.VisitStmt(Clause.getConditionExpr());
2622 } else {
2623 for (auto *E : Clause.getVarList())
2624 Profiler.VisitStmt(E);
2625 }
2626}
2627
2628void OpenACCClauseProfiler::VisitFinalizeClause(
2629 const OpenACCFinalizeClause &Clause) {}
2630
2631void OpenACCClauseProfiler::VisitIfPresentClause(
2632 const OpenACCIfPresentClause &Clause) {}
2633
2634void OpenACCClauseProfiler::VisitNumGangsClause(
2635 const OpenACCNumGangsClause &Clause) {
2636 for (auto *E : Clause.getIntExprs())
2637 Profiler.VisitStmt(E);
2638}
2639
2640void OpenACCClauseProfiler::VisitTileClause(const OpenACCTileClause &Clause) {
2641 for (auto *E : Clause.getSizeExprs())
2642 Profiler.VisitStmt(E);
2643}
2644
2645void OpenACCClauseProfiler::VisitNumWorkersClause(
2646 const OpenACCNumWorkersClause &Clause) {
2647 assert(Clause.hasIntExpr() && "num_workers clause requires a valid int expr");
2648 Profiler.VisitStmt(Clause.getIntExpr());
2649}
2650
2651void OpenACCClauseProfiler::VisitCollapseClause(
2652 const OpenACCCollapseClause &Clause) {
2653 assert(Clause.getLoopCount() && "collapse clause requires a valid int expr");
2654 Profiler.VisitStmt(Clause.getLoopCount());
2655}
2656
2657void OpenACCClauseProfiler::VisitPrivateClause(
2658 const OpenACCPrivateClause &Clause) {
2659 VisitClauseWithVarList(Clause);
2660
2661 for (auto &Recipe : Clause.getInitRecipes()) {
2662 Profiler.VisitDecl(Recipe.AllocaDecl);
2663 }
2664}
2665
2666void OpenACCClauseProfiler::VisitFirstPrivateClause(
2667 const OpenACCFirstPrivateClause &Clause) {
2668 VisitClauseWithVarList(Clause);
2669
2670 for (auto &Recipe : Clause.getInitRecipes()) {
2671 Profiler.VisitDecl(Recipe.AllocaDecl);
2672 Profiler.VisitDecl(Recipe.InitFromTemporary);
2673 }
2674}
2675
2676void OpenACCClauseProfiler::VisitAttachClause(
2677 const OpenACCAttachClause &Clause) {
2678 VisitClauseWithVarList(Clause);
2679}
2680
2681void OpenACCClauseProfiler::VisitDetachClause(
2682 const OpenACCDetachClause &Clause) {
2683 VisitClauseWithVarList(Clause);
2684}
2685
2686void OpenACCClauseProfiler::VisitDeleteClause(
2687 const OpenACCDeleteClause &Clause) {
2688 VisitClauseWithVarList(Clause);
2689}
2690
2691void OpenACCClauseProfiler::VisitDevicePtrClause(
2692 const OpenACCDevicePtrClause &Clause) {
2693 VisitClauseWithVarList(Clause);
2694}
2695
2696void OpenACCClauseProfiler::VisitNoCreateClause(
2697 const OpenACCNoCreateClause &Clause) {
2698 VisitClauseWithVarList(Clause);
2699}
2700
2701void OpenACCClauseProfiler::VisitPresentClause(
2702 const OpenACCPresentClause &Clause) {
2703 VisitClauseWithVarList(Clause);
2704}
2705
2706void OpenACCClauseProfiler::VisitUseDeviceClause(
2707 const OpenACCUseDeviceClause &Clause) {
2708 VisitClauseWithVarList(Clause);
2709}
2710
2711void OpenACCClauseProfiler::VisitVectorLengthClause(
2712 const OpenACCVectorLengthClause &Clause) {
2713 assert(Clause.hasIntExpr() &&
2714 "vector_length clause requires a valid int expr");
2715 Profiler.VisitStmt(Clause.getIntExpr());
2716}
2717
2718void OpenACCClauseProfiler::VisitAsyncClause(const OpenACCAsyncClause &Clause) {
2719 if (Clause.hasIntExpr())
2720 Profiler.VisitStmt(Clause.getIntExpr());
2721}
2722
2723void OpenACCClauseProfiler::VisitDeviceNumClause(
2724 const OpenACCDeviceNumClause &Clause) {
2725 Profiler.VisitStmt(Clause.getIntExpr());
2726}
2727
2728void OpenACCClauseProfiler::VisitDefaultAsyncClause(
2729 const OpenACCDefaultAsyncClause &Clause) {
2730 Profiler.VisitStmt(Clause.getIntExpr());
2731}
2732
2733void OpenACCClauseProfiler::VisitWorkerClause(
2734 const OpenACCWorkerClause &Clause) {
2735 if (Clause.hasIntExpr())
2736 Profiler.VisitStmt(Clause.getIntExpr());
2737}
2738
2739void OpenACCClauseProfiler::VisitVectorClause(
2740 const OpenACCVectorClause &Clause) {
2741 if (Clause.hasIntExpr())
2742 Profiler.VisitStmt(Clause.getIntExpr());
2743}
2744
2745void OpenACCClauseProfiler::VisitWaitClause(const OpenACCWaitClause &Clause) {
2746 if (Clause.hasDevNumExpr())
2747 Profiler.VisitStmt(Clause.getDevNumExpr());
2748 for (auto *E : Clause.getQueueIdExprs())
2749 Profiler.VisitStmt(E);
2750}
2751
2752/// Nothing to do here, there are no sub-statements.
2753void OpenACCClauseProfiler::VisitDeviceTypeClause(
2754 const OpenACCDeviceTypeClause &Clause) {}
2755
2756void OpenACCClauseProfiler::VisitAutoClause(const OpenACCAutoClause &Clause) {}
2757
2758void OpenACCClauseProfiler::VisitIndependentClause(
2759 const OpenACCIndependentClause &Clause) {}
2760
2761void OpenACCClauseProfiler::VisitSeqClause(const OpenACCSeqClause &Clause) {}
2762void OpenACCClauseProfiler::VisitNoHostClause(
2763 const OpenACCNoHostClause &Clause) {}
2764
2765void OpenACCClauseProfiler::VisitGangClause(const OpenACCGangClause &Clause) {
2766 for (unsigned I = 0; I < Clause.getNumExprs(); ++I) {
2767 Profiler.VisitStmt(Clause.getExpr(I).second);
2768 }
2769}
2770
2771void OpenACCClauseProfiler::VisitReductionClause(
2772 const OpenACCReductionClause &Clause) {
2773 VisitClauseWithVarList(Clause);
2774
2775 for (auto &Recipe : Clause.getRecipes()) {
2776 Profiler.VisitDecl(Recipe.AllocaDecl);
2777
2778 // TODO: OpenACC: Make sure we remember to update this when we figure out
2779 // what we're adding for the operation recipe, in the meantime, a static
2780 // assert will make sure we don't add something.
2781 static_assert(sizeof(OpenACCReductionRecipe::CombinerRecipe) ==
2782 3 * sizeof(int *));
2783 for (auto &CombinerRecipe : Recipe.CombinerRecipes) {
2784 if (CombinerRecipe.Op) {
2785 Profiler.VisitDecl(CombinerRecipe.LHS);
2786 Profiler.VisitDecl(CombinerRecipe.RHS);
2787 Profiler.VisitStmt(CombinerRecipe.Op);
2788 }
2789 }
2790 }
2791}
2792
2793void OpenACCClauseProfiler::VisitBindClause(const OpenACCBindClause &Clause) {
2794 assert(false && "not implemented... what can we do about our expr?");
2795}
2796} // namespace
2797
2798void StmtProfiler::VisitOpenACCComputeConstruct(
2799 const OpenACCComputeConstruct *S) {
2800 // VisitStmt handles children, so the AssociatedStmt is handled.
2801 VisitStmt(S);
2802
2803 OpenACCClauseProfiler P{*this};
2804 P.VisitOpenACCClauseList(S->clauses());
2805}
2806
2807void StmtProfiler::VisitOpenACCLoopConstruct(const OpenACCLoopConstruct *S) {
2808 // VisitStmt handles children, so the Loop is handled.
2809 VisitStmt(S);
2810
2811 OpenACCClauseProfiler P{*this};
2812 P.VisitOpenACCClauseList(S->clauses());
2813}
2814
2815void StmtProfiler::VisitOpenACCCombinedConstruct(
2816 const OpenACCCombinedConstruct *S) {
2817 // VisitStmt handles children, so the Loop is handled.
2818 VisitStmt(S);
2819
2820 OpenACCClauseProfiler P{*this};
2821 P.VisitOpenACCClauseList(S->clauses());
2822}
2823
2824void StmtProfiler::VisitOpenACCDataConstruct(const OpenACCDataConstruct *S) {
2825 VisitStmt(S);
2826
2827 OpenACCClauseProfiler P{*this};
2828 P.VisitOpenACCClauseList(S->clauses());
2829}
2830
2831void StmtProfiler::VisitOpenACCEnterDataConstruct(
2832 const OpenACCEnterDataConstruct *S) {
2833 VisitStmt(S);
2834
2835 OpenACCClauseProfiler P{*this};
2836 P.VisitOpenACCClauseList(S->clauses());
2837}
2838
2839void StmtProfiler::VisitOpenACCExitDataConstruct(
2840 const OpenACCExitDataConstruct *S) {
2841 VisitStmt(S);
2842
2843 OpenACCClauseProfiler P{*this};
2844 P.VisitOpenACCClauseList(S->clauses());
2845}
2846
2847void StmtProfiler::VisitOpenACCHostDataConstruct(
2848 const OpenACCHostDataConstruct *S) {
2849 VisitStmt(S);
2850
2851 OpenACCClauseProfiler P{*this};
2852 P.VisitOpenACCClauseList(S->clauses());
2853}
2854
2855void StmtProfiler::VisitOpenACCWaitConstruct(const OpenACCWaitConstruct *S) {
2856 // VisitStmt covers 'children', so the exprs inside of it are covered.
2857 VisitStmt(S);
2858
2859 OpenACCClauseProfiler P{*this};
2860 P.VisitOpenACCClauseList(S->clauses());
2861}
2862
2863void StmtProfiler::VisitOpenACCCacheConstruct(const OpenACCCacheConstruct *S) {
2864 // VisitStmt covers 'children', so the exprs inside of it are covered.
2865 VisitStmt(S);
2866}
2867
2868void StmtProfiler::VisitOpenACCInitConstruct(const OpenACCInitConstruct *S) {
2869 VisitStmt(S);
2870 OpenACCClauseProfiler P{*this};
2871 P.VisitOpenACCClauseList(S->clauses());
2872}
2873
2874void StmtProfiler::VisitOpenACCShutdownConstruct(
2875 const OpenACCShutdownConstruct *S) {
2876 VisitStmt(S);
2877 OpenACCClauseProfiler P{*this};
2878 P.VisitOpenACCClauseList(S->clauses());
2879}
2880
2881void StmtProfiler::VisitOpenACCSetConstruct(const OpenACCSetConstruct *S) {
2882 VisitStmt(S);
2883 OpenACCClauseProfiler P{*this};
2884 P.VisitOpenACCClauseList(S->clauses());
2885}
2886
2887void StmtProfiler::VisitOpenACCUpdateConstruct(
2888 const OpenACCUpdateConstruct *S) {
2889 VisitStmt(S);
2890 OpenACCClauseProfiler P{*this};
2891 P.VisitOpenACCClauseList(S->clauses());
2892}
2893
2894void StmtProfiler::VisitOpenACCAtomicConstruct(
2895 const OpenACCAtomicConstruct *S) {
2896 VisitStmt(S);
2897 OpenACCClauseProfiler P{*this};
2898 P.VisitOpenACCClauseList(S->clauses());
2899}
2900
2901void StmtProfiler::VisitHLSLOutArgExpr(const HLSLOutArgExpr *S) {
2902 VisitStmt(S);
2903}
2904
2905void Stmt::Profile(llvm::FoldingSetNodeID &ID, const ASTContext &Context,
2906 bool Canonical, bool ProfileLambdaExpr) const {
2907 StmtProfilerWithPointers Profiler(ID, Context, Canonical, ProfileLambdaExpr);
2908 Profiler.Visit(this);
2909}
2910
2911void Stmt::ProcessODRHash(llvm::FoldingSetNodeID &ID,
2912 class ODRHash &Hash) const {
2913 StmtProfilerWithoutPointers Profiler(ID, Hash);
2914 Profiler.Visit(this);
2915}
Defines the clang::ASTContext interface.
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....
Defines the C++ template declaration subclasses.
Defines the clang::Expr interface and subclasses for C++ expressions.
This file contains the declaration of the ODRHash class, which calculates a hash based on AST nodes,...
This file defines OpenMP AST classes for clauses.
static Stmt::StmtClass DecodeOperatorCall(const CXXOperatorCallExpr *S, UnaryOperatorKind &UnaryOp, BinaryOperatorKind &BinaryOp, unsigned &NumArgs)
static const TemplateArgument & getArgument(const TemplateArgument &A)
llvm::APInt getValue() const
void Profile(llvm::FoldingSetNodeID &ID) const
profile this value.
Definition APValue.cpp:489
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition ASTContext.h:220
LabelDecl * getLabel() const
Definition Expr.h:4507
ArrayTypeTrait getTrait() const
Definition ExprCXX.h:3038
QualType getQueriedType() const
Definition ExprCXX.h:3042
bool isVolatile() const
Definition Stmt.h:3272
unsigned getNumClobbers() const
Definition Stmt.h:3317
unsigned getNumOutputs() const
Definition Stmt.h:3285
unsigned getNumInputs() const
Definition Stmt.h:3307
bool isSimple() const
Definition Stmt.h:3269
AtomicOp getOp() const
Definition Expr.h:6877
Opcode getOpcode() const
Definition Expr.h:4017
const BlockDecl * getBlockDecl() const
Definition Expr.h:6570
CXXTemporary * getTemporary()
Definition ExprCXX.h:1512
bool getValue() const
Definition ExprCXX.h:740
QualType getCaughtType() const
Definition StmtCXX.cpp:19
bool isElidable() const
Whether this construction is elidable.
Definition ExprCXX.h:1618
CXXConstructorDecl * getConstructor() const
Get the constructor that this expression will (ultimately) call.
Definition ExprCXX.h:1612
const ParmVarDecl * getParam() const
Definition ExprCXX.h:1313
FieldDecl * getField()
Get the field whose initializer will be used.
Definition ExprCXX.h:1412
FunctionDecl * getOperatorDelete() const
Definition ExprCXX.h:2667
bool isArrayForm() const
Definition ExprCXX.h:2654
bool isGlobalDelete() const
Definition ExprCXX.h:2653
bool isArrow() const
Determine whether this member expression used the '->' operator; otherwise, it used the '.
Definition ExprCXX.h:3971
NestedNameSpecifier getQualifier() const
Retrieve the nested-name-specifier that qualifies the member name.
Definition ExprCXX.h:3979
unsigned getNumTemplateArgs() const
Retrieve the number of template arguments provided as part of this template-id.
Definition ExprCXX.h:4066
const TemplateArgumentLoc * getTemplateArgs() const
Retrieve the template arguments provided as part of this template-id.
Definition ExprCXX.h:4057
bool hasExplicitTemplateArgs() const
Determines whether this member expression actually had a C++ template argument list explicitly specif...
Definition ExprCXX.h:4045
DeclarationName getMember() const
Retrieve the name of the member that this expression refers to.
Definition ExprCXX.h:4010
bool isImplicitAccess() const
True if this is an implicit access, i.e.
Definition ExprCXX.h:3954
BinaryOperatorKind getOperator() const
Definition ExprCXX.h:5079
CXXConstructorDecl * getConstructor() const
Get the constructor that this expression will call.
Definition ExprCXX.h:1790
bool isArray() const
Definition ExprCXX.h:2466
QualType getAllocatedType() const
Definition ExprCXX.h:2436
CXXNewInitializationStyle getInitializationStyle() const
The kind of initializer this new-expression has.
Definition ExprCXX.h:2529
FunctionDecl * getOperatorDelete() const
Definition ExprCXX.h:2463
unsigned getNumPlacementArgs() const
Definition ExprCXX.h:2496
bool isParenTypeId() const
Definition ExprCXX.h:2517
FunctionDecl * getOperatorNew() const
Definition ExprCXX.h:2461
bool isGlobalNew() const
Definition ExprCXX.h:2523
A call to an overloaded operator written using operator syntax.
Definition ExprCXX.h:84
OverloadedOperatorKind getOperator() const
Returns the kind of overloaded operator that this expression refers to.
Definition ExprCXX.h:114
TypeSourceInfo * getDestroyedTypeInfo() const
Retrieve the source location information for the type being destroyed.
Definition ExprCXX.h:2841
bool isArrow() const
Determine whether this pseudo-destructor expression was written using an '->' (otherwise,...
Definition ExprCXX.h:2811
TypeSourceInfo * getScopeTypeInfo() const
Retrieve the scope type in a qualified pseudo-destructor expression.
Definition ExprCXX.h:2825
QualType getDestroyedType() const
Retrieve the type being destroyed.
Definition ExprCXX.cpp:385
NestedNameSpecifier getQualifier() const
If the member name was qualified, retrieves the nested-name-specifier that precedes the member name.
Definition ExprCXX.h:2805
const IdentifierInfo * getDestroyedTypeIdentifier() const
In a dependent pseudo-destructor expression for which we do not have full type information on the des...
Definition ExprCXX.h:2848
capture_const_range captures() const
Definition DeclCXX.h:1097
Expr * getSemanticForm()
Get an equivalent semantic form for this expression.
Definition ExprCXX.h:304
bool isReversed() const
Determine whether this expression was rewritten in reverse form.
Definition ExprCXX.h:322
const CXXDestructorDecl * getDestructor() const
Definition ExprCXX.h:1471
bool isCapturedByCopyInLambdaWithExplicitObjectParameter() const
Definition ExprCXX.h:1181
bool isImplicit() const
Definition ExprCXX.h:1178
bool isTypeOperand() const
Definition ExprCXX.h:884
TypeSourceInfo * getTypeOperandSourceInfo() const
Retrieve source information for the type operand.
Definition ExprCXX.h:891
bool isListInitialization() const
Determine whether this expression models list-initialization.
Definition ExprCXX.h:3801
QualType getTypeAsWritten() const
Retrieve the type that is being constructed, as specified in the source code.
Definition ExprCXX.h:3780
bool isTypeOperand() const
Definition ExprCXX.h:1099
TypeSourceInfo * getTypeOperandSourceInfo() const
Retrieve source information for the type operand.
Definition ExprCXX.h:1106
Expr * getArg(unsigned Arg)
getArg - Return the specified argument.
Definition Expr.h:3081
unsigned getNumArgs() const
getNumArgs - Return the number of actual arguments to this call.
Definition Expr.h:3068
unsigned getValue() const
Definition Expr.h:1629
CharacterLiteralKind getKind() const
Definition Expr.h:1622
bool isFileScope() const
Definition Expr.h:3571
ArrayRef< TemplateArgument > getTemplateArguments() const
ConceptDecl * getNamedConcept() const
ConstStmtVisitor - This class implements a simple visitor for Stmt subclasses.
decl_range decls() const
decls_begin/decls_end - Iterate over the declarations stored in this context.
Definition DeclBase.h:2373
unsigned getNumTemplateArgs() const
Retrieve the number of template arguments provided as part of this template-id.
Definition Expr.h:1445
bool hasExplicitTemplateArgs() const
Determines whether this declaration reference was followed by an explicit template argument list.
Definition Expr.h:1425
NestedNameSpecifier getQualifier() const
If the name was qualified, retrieves the nested-name-specifier that precedes the name.
Definition Expr.h:1371
ValueDecl * getDecl()
Definition Expr.h:1338
const TemplateArgumentLoc * getTemplateArgs() const
Retrieve the template arguments provided as part of this template-id.
Definition Expr.h:1437
decl_range decls()
Definition Stmt.h:1659
Decl - This represents one declaration (or definition), e.g.
Definition DeclBase.h:86
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
Definition DeclBase.h:978
Kind getKind() const
Definition DeclBase.h:442
The name of a declaration.
void * getAsOpaquePtr() const
Get the representation of this declaration name as an opaque pointer.
bool hasExplicitTemplateArgs() const
Determines whether this lookup had explicit template arguments.
Definition ExprCXX.h:3596
NestedNameSpecifier getQualifier() const
Retrieve the nested-name-specifier that qualifies this declaration.
Definition ExprCXX.h:3564
unsigned getNumTemplateArgs() const
Definition ExprCXX.h:3613
DeclarationName getDeclName() const
Retrieve the name that this expression refers to.
Definition ExprCXX.h:3551
TemplateArgumentLoc const * getTemplateArgs() const
Definition ExprCXX.h:3606
bool usesGNUSyntax() const
Determines whether this designated initializer used the deprecated GNU syntax for designated initiali...
Definition Expr.h:5749
MutableArrayRef< Designator > designators()
Definition Expr.h:5718
TypeSourceInfo * getTypeInfoAsWritten() const
getTypeInfoAsWritten - Returns the type source info for the type that this expression is casting to.
Definition Expr.h:3884
QualType getTypeAsWritten() const
getTypeAsWritten - Returns the type that this expression is casting to, as written in the source code...
Definition Expr.h:3889
ExprValueKind getValueKind() const
getValueKind - The value kind that this expression produces.
Definition Expr.h:444
bool isTypeDependent() const
Determines whether the type of this expression depends on.
Definition Expr.h:194
QualType getType() const
Definition Expr.h:144
Expr * getQueriedExpression() const
Definition ExprCXX.h:3110
ExpressionTrait getTrait() const
Definition ExprCXX.h:3106
IdentifierInfo & getAccessor() const
Definition Expr.h:6519
llvm::APInt getValue() const
Returns an internal integer representation of the literal.
Definition Expr.h:1575
llvm::APFloat getValue() const
Definition Expr.h:1666
bool isExact() const
Definition Expr.h:1699
const Expr * getSubExpr() const
Definition Expr.h:1062
ValueDecl *const * iterator
Iterators over the parameters which the parameter pack expanded into.
Definition ExprCXX.h:4876
ValueDecl * getParameterPack() const
Get the parameter pack which this expression refers to.
Definition ExprCXX.h:4869
iterator end() const
Definition ExprCXX.h:4878
unsigned getNumExpansions() const
Get the number of parameters in this parameter pack.
Definition ExprCXX.h:4881
iterator begin() const
Definition ExprCXX.h:4877
unsigned getNumLabels() const
Definition Stmt.h:3545
labels_range labels()
Definition Stmt.h:3568
const Expr * getOutputConstraintExpr(unsigned i) const
Definition Stmt.h:3497
StringRef getInputName(unsigned i) const
Definition Stmt.h:3514
StringRef getOutputName(unsigned i) const
Definition Stmt.h:3488
const Expr * getInputConstraintExpr(unsigned i) const
Definition Stmt.h:3523
const Expr * getAsmStringExpr() const
Definition Stmt.h:3422
Expr * getClobberExpr(unsigned i)
Definition Stmt.h:3602
association_range associations()
Definition Expr.h:6443
AssociationTy< true > ConstAssociation
Definition Expr.h:6344
LabelDecl * getLabel() const
Definition Stmt.h:2982
One of these records is kept for each identifier that is lexed.
VarDecl * getConditionVariable()
Retrieve the variable declared in this "if" statement, if any.
Definition Stmt.cpp:1030
InitListExpr * getSyntacticForm() const
Definition Expr.h:5406
LabelDecl * getDecl() const
Definition Stmt.h:2164
CXXRecordDecl * getLambdaClass() const
Retrieve the class that corresponds to the lambda.
Definition ExprCXX.cpp:1400
bool isIfExists() const
Determine whether this is an __if_exists statement.
Definition StmtCXX.h:278
DeclarationNameInfo getNameInfo() const
Retrieve the name of the entity we're testing for, along with location information.
Definition StmtCXX.h:289
NestedNameSpecifierLoc getQualifierLoc() const
Retrieve the nested-name-specifier that qualifies this name, if any.
Definition StmtCXX.h:285
MSPropertyDecl * getPropertyDecl() const
Definition ExprCXX.h:990
NestedNameSpecifier getQualifier() const
If the member name was qualified, retrieves the nested-name-specifier that precedes the member name.
Definition Expr.h:3409
ValueDecl * getMemberDecl() const
Retrieve the member declaration to which this expression refers.
Definition Expr.h:3381
bool isArrow() const
Definition Expr.h:3482
NestedNameSpecifier getNestedNameSpecifier() const
Retrieve the nested-name-specifier to which this instance refers.
Represents a C++ nested name specifier, such as "\::std::vector<int>::".
NestedNameSpecifier getCanonical() const
Retrieves the "canonical" nested name specifier for a given nested name specifier.
void Profile(llvm::FoldingSetNodeID &ID) const
void AddFunctionDecl(const FunctionDecl *Function, bool SkipBody=false)
Definition ODRHash.cpp:670
unsigned CalculateHash()
Definition ODRHash.cpp:231
Class that handles post-update expression for some clauses, like 'lastprivate', 'reduction' etc.
Class that handles pre-initialization statement for some clauses, like 'schedule',...
unsigned numOfIterators() const
Returns number of iterator definitions.
Definition ExprOpenMP.h:275
Decl * getIteratorDecl(unsigned I)
Gets the iterator declaration for the given iterator.
Definition Expr.cpp:5428
const VarDecl * getCatchParamDecl() const
Definition StmtObjC.h:97
bool hasEllipsis() const
Definition StmtObjC.h:113
ObjCBridgeCastKind getBridgeKind() const
Determine which kind of bridge is being performed via this cast.
Definition ExprObjC.h:1669
QualType getEncodedType() const
Definition ExprObjC.h:428
bool shouldCopy() const
shouldCopy - True if we should do the 'copy' part of the copy-restore.
Definition ExprObjC.h:1610
bool isArrow() const
Definition ExprObjC.h:1525
ObjCIvarDecl * getDecl()
Definition ExprObjC.h:578
bool isArrow() const
Definition ExprObjC.h:586
bool isFreeIvar() const
Definition ExprObjC.h:587
Selector getSelector() const
Definition ExprObjC.cpp:289
const ObjCMethodDecl * getMethodDecl() const
Definition ExprObjC.h:1364
ObjCPropertyDecl * getExplicitProperty() const
Definition ExprObjC.h:705
ObjCMethodDecl * getImplicitPropertyGetter() const
Definition ExprObjC.h:710
QualType getSuperReceiverType() const
Definition ExprObjC.h:761
bool isImplicitProperty() const
Definition ExprObjC.h:702
ObjCMethodDecl * getImplicitPropertySetter() const
Definition ExprObjC.h:715
bool isSuperReceiver() const
Definition ExprObjC.h:770
ObjCProtocolDecl * getProtocol() const
Definition ExprObjC.h:521
Selector getSelector() const
Definition ExprObjC.h:468
ObjCMethodDecl * getAtIndexMethodDecl() const
Definition ExprObjC.h:884
ObjCMethodDecl * setAtIndexMethodDecl() const
Definition ExprObjC.h:888
const OffsetOfNode & getComponent(unsigned Idx) const
Definition Expr.h:2574
TypeSourceInfo * getTypeSourceInfo() const
Definition Expr.h:2567
unsigned getNumComponents() const
Definition Expr.h:2582
FieldDecl * getField() const
For a field offsetof node, returns the field.
Definition Expr.h:2485
IdentifierInfo * getFieldName() const
For a field or identifier offsetof node, returns the name of the field.
Definition Expr.cpp:1684
@ Array
An index into an array.
Definition Expr.h:2426
@ Identifier
A field in a dependent type, known only by its name.
Definition Expr.h:2430
@ Field
A field.
Definition Expr.h:2428
@ Base
An implicit indirection through a C++ base class, when the field found is in a base class.
Definition Expr.h:2433
Kind getKind() const
Determine what kind of offsetof node this is.
Definition Expr.h:2475
const Expr * getConditionExpr() const
ArrayRef< Expr * > getVarList()
const Expr * getLoopCount() const
ArrayRef< OpenACCFirstPrivateRecipe > getInitRecipes()
unsigned getNumExprs() const
std::pair< OpenACCGangKind, const Expr * > getExpr(unsigned I) const
ArrayRef< Expr * > getIntExprs()
ArrayRef< OpenACCPrivateRecipe > getInitRecipes()
ArrayRef< OpenACCReductionRecipe > getRecipes()
const Expr * getConditionExpr() const
bool isConditionExprClause() const
ArrayRef< Expr * > getVarList()
ArrayRef< Expr * > getSizeExprs()
ArrayRef< Expr * > getQueueIdExprs()
Expr * getDevNumExpr() const
bool hasExplicitTemplateArgs() const
Determines whether this expression had explicit template arguments.
Definition ExprCXX.h:3282
NestedNameSpecifier getQualifier() const
Fetches the nested-name qualifier, if one was given.
Definition ExprCXX.h:3246
decls_iterator decls_begin() const
Definition ExprCXX.h:3223
unsigned getNumDecls() const
Gets the number of declarations in the unresolved set.
Definition ExprCXX.h:3234
TemplateArgumentLoc const * getTemplateArgs() const
Definition ExprCXX.h:3326
unsigned getNumTemplateArgs() const
Definition ExprCXX.h:3332
DeclarationName getName() const
Gets the name looked up.
Definition ExprCXX.h:3240
Expr * getIndexExpr() const
Definition ExprCXX.h:4630
ArrayRef< Expr * > getExpressions() const
Return the trailing expressions, regardless of the expansion.
Definition ExprCXX.h:4648
bool expandsToEmptyPack() const
Determine if the expression was expanded to empty.
Definition ExprCXX.h:4609
Expr * getPackIdExpression() const
Definition ExprCXX.h:4626
PredefinedIdentKind getIdentKind() const
Definition Expr.h:2040
semantics_iterator semantics_end()
Definition Expr.h:6755
semantics_iterator semantics_begin()
Definition Expr.h:6751
const Expr *const * const_semantics_iterator
Definition Expr.h:6750
A (possibly-)qualified type.
Definition TypeBase.h:937
ArrayRef< concepts::Requirement * > getRequirements() const
ArrayRef< ParmVarDecl * > getLocalParameters() const
TypeSourceInfo * getTypeSourceInfo()
Definition Expr.h:2143
bool isPartiallySubstituted() const
Determine whether this represents a partially-substituted sizeof... expression, such as is produced f...
Definition ExprCXX.h:4528
ArrayRef< TemplateArgument > getPartialArguments() const
Get.
Definition ExprCXX.h:4533
NamedDecl * getPack() const
Retrieve the parameter pack.
Definition ExprCXX.h:4511
Stmt - This represents one statement.
Definition Stmt.h:85
void ProcessODRHash(llvm::FoldingSetNodeID &ID, ODRHash &Hash) const
Calculate a unique representation for a statement that is stable across compiler invocations.
child_range children()
Definition Stmt.cpp:299
StmtClass getStmtClass() const
Definition Stmt.h:1472
void Profile(llvm::FoldingSetNodeID &ID, const ASTContext &Context, bool Canonical, bool ProfileLambdaExpr=false) const
Produce a unique representation of the given statement.
StringLiteralKind getKind() const
Definition Expr.h:1912
StringRef getBytes() const
Allow access to clients that need the byte representation, such as ASTWriterStmt::VisitStringLiteral(...
Definition Expr.h:1875
TemplateArgument getArgumentPack() const
Retrieve the template argument pack containing the substituted template arguments.
Definition ExprCXX.cpp:1799
NonTypeTemplateParmDecl * getParameterPack() const
Retrieve the non-type template parameter pack being substituted.
Definition ExprCXX.cpp:1794
VarDecl * getConditionVariable()
Retrieve the variable declared in this "switch" statement, if any.
Definition Stmt.cpp:1148
Location wrapper for a TemplateArgument.
Represents a template argument.
QualType getStructuralValueType() const
Get the type of a StructuralValue.
QualType getParamTypeForDecl() const
Expr * getAsExpr() const
Retrieve the template argument as an expression.
QualType getAsType() const
Retrieve the type for a type template argument.
llvm::APSInt getAsIntegral() const
Retrieve the template argument as an integral value.
QualType getNullPtrType() const
Retrieve the type for null non-type template argument.
QualType getIntegralType() const
Retrieve the type of the integral value.
ValueDecl * getAsDecl() const
Retrieve the declaration for a declaration non-type template argument.
ArrayRef< TemplateArgument > pack_elements() const
Iterator range referencing all of the elements of a template argument pack.
@ Declaration
The template argument is a declaration that was provided for a pointer, reference,...
@ Template
The template argument is a template name that was provided for a template template parameter.
@ StructuralValue
The template argument is a non-type template argument that can't be represented by the special-case D...
@ Pack
The template argument is actually a parameter pack.
@ TemplateExpansion
The template argument is a pack expansion of a template name that was provided for a template templat...
@ NullPtr
The template argument is a null pointer or null pointer to member that was provided for a non-type te...
@ Type
The template argument is a type.
@ Null
Represents an empty template argument, e.g., one that has not been deduced.
@ Integral
The template argument is an integral value stored in an llvm::APSInt that was provided for an integra...
@ Expression
The template argument is an expression, and we've not resolved it to one of the other forms yet,...
ArgKind getKind() const
Return the kind of stored template argument.
TemplateName getAsTemplateOrTemplatePattern() const
Retrieve the template argument as a template name; if the argument is a pack expansion,...
const APValue & getAsStructuralValue() const
Get the value of a StructuralValue.
Represents a C++ template name within the type system.
void Profile(llvm::FoldingSetNodeID &ID)
Expr * getImmediatelyDeclaredConstraint() const
Get the immediately-declared constraint expression introduced by this type-constraint,...
Definition ASTConcept.h:244
QualType getType() const
Return the type wrapped by this type source info.
Definition TypeBase.h:8260
TypeSourceInfo * getArg(unsigned I) const
Retrieve the Ith argument.
Definition ExprCXX.h:2963
unsigned getNumArgs() const
Determine the number of arguments to this type trait.
Definition ExprCXX.h:2960
TypeTrait getTrait() const
Determine which type trait this expression uses.
Definition ExprCXX.h:2941
const T * castAs() const
Member-template castAs<specific type>.
Definition TypeBase.h:9158
TypeClass getTypeClass() const
Definition TypeBase.h:2385
const T * getAs() const
Member-template getAs<specific type>'.
Definition TypeBase.h:9091
QualType getArgumentType() const
Definition Expr.h:2668
UnaryExprOrTypeTrait getKind() const
Definition Expr.h:2657
Opcode getOpcode() const
Definition Expr.h:2280
DeclarationName getMemberName() const
Retrieve the name of the member that this expression refers to.
Definition ExprCXX.h:4236
bool isArrow() const
Determine whether this member expression used the '->' operator; otherwise, it used the '.
Definition ExprCXX.h:4220
bool isImplicitAccess() const
True if this is an implicit access, i.e., one in which the member being accessed was not written in t...
Definition ExprCXX.cpp:1645
QualType getType() const
Definition Decl.h:723
VarDecl * getConditionVariable()
Retrieve the variable declared in this "while" statement, if any.
Definition Stmt.cpp:1209
The JSON file list parser is used to communicate input to InstallAPI.
@ OO_None
Not an overloaded operator.
@ NUM_OVERLOADED_OPERATORS
bool isa(CodeGen::Address addr)
Definition Address.h:330
@ TemplateName
The identifier is a template name. FIXME: Add an annotation for that.
Definition Parser.h:61
OpenACCComputeConstruct(OpenACCDirectiveKind K, SourceLocation Start, SourceLocation DirectiveLoc, SourceLocation End, ArrayRef< const OpenACCClause * > Clauses, Stmt *StructuredBlock)
const FunctionProtoType * T
U cast(CodeGen::Address addr)
Definition Address.h:327
#define false
Definition stdbool.h:26
DeclarationName getName() const
getName - Returns the embedded declaration name.
Expr * AllocatorTraits
Allocator traits.