Coverage Report

Created: 2021-08-24 07:12

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/lib/AST/StmtPrinter.cpp
Line
Count
Source (jump to first uncovered line)
1
//===- StmtPrinter.cpp - Printing 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::dumpPretty/Stmt::printPretty methods, which
10
// pretty print the AST back out to C code.
11
//
12
//===----------------------------------------------------------------------===//
13
14
#include "clang/AST/ASTContext.h"
15
#include "clang/AST/Attr.h"
16
#include "clang/AST/Decl.h"
17
#include "clang/AST/DeclBase.h"
18
#include "clang/AST/DeclCXX.h"
19
#include "clang/AST/DeclObjC.h"
20
#include "clang/AST/DeclOpenMP.h"
21
#include "clang/AST/DeclTemplate.h"
22
#include "clang/AST/Expr.h"
23
#include "clang/AST/ExprCXX.h"
24
#include "clang/AST/ExprObjC.h"
25
#include "clang/AST/ExprOpenMP.h"
26
#include "clang/AST/NestedNameSpecifier.h"
27
#include "clang/AST/OpenMPClause.h"
28
#include "clang/AST/PrettyPrinter.h"
29
#include "clang/AST/Stmt.h"
30
#include "clang/AST/StmtCXX.h"
31
#include "clang/AST/StmtObjC.h"
32
#include "clang/AST/StmtOpenMP.h"
33
#include "clang/AST/StmtVisitor.h"
34
#include "clang/AST/TemplateBase.h"
35
#include "clang/AST/Type.h"
36
#include "clang/Basic/CharInfo.h"
37
#include "clang/Basic/ExpressionTraits.h"
38
#include "clang/Basic/IdentifierTable.h"
39
#include "clang/Basic/JsonSupport.h"
40
#include "clang/Basic/LLVM.h"
41
#include "clang/Basic/Lambda.h"
42
#include "clang/Basic/OpenMPKinds.h"
43
#include "clang/Basic/OperatorKinds.h"
44
#include "clang/Basic/SourceLocation.h"
45
#include "clang/Basic/TypeTraits.h"
46
#include "clang/Lex/Lexer.h"
47
#include "llvm/ADT/ArrayRef.h"
48
#include "llvm/ADT/SmallString.h"
49
#include "llvm/ADT/SmallVector.h"
50
#include "llvm/ADT/StringExtras.h"
51
#include "llvm/ADT/StringRef.h"
52
#include "llvm/Support/Casting.h"
53
#include "llvm/Support/Compiler.h"
54
#include "llvm/Support/ErrorHandling.h"
55
#include "llvm/Support/raw_ostream.h"
56
#include <cassert>
57
#include <string>
58
59
using namespace clang;
60
61
//===----------------------------------------------------------------------===//
62
// StmtPrinter Visitor
63
//===----------------------------------------------------------------------===//
64
65
namespace {
66
67
  class StmtPrinter : public StmtVisitor<StmtPrinter> {
68
    raw_ostream &OS;
69
    unsigned IndentLevel;
70
    PrinterHelper* Helper;
71
    PrintingPolicy Policy;
72
    std::string NL;
73
    const ASTContext *Context;
74
75
  public:
76
    StmtPrinter(raw_ostream &os, PrinterHelper *helper,
77
                const PrintingPolicy &Policy, unsigned Indentation = 0,
78
                StringRef NL = "\n", const ASTContext *Context = nullptr)
79
        : OS(os), IndentLevel(Indentation), Helper(helper), Policy(Policy),
80
110k
          NL(NL), Context(Context) {}
81
82
36.7k
    void PrintStmt(Stmt *S) { PrintStmt(S, Policy.Indentation); }
83
84
36.8k
    void PrintStmt(Stmt *S, int SubIndent) {
85
36.8k
      IndentLevel += SubIndent;
86
36.8k
      if (S && isa<Expr>(S)) {
87
        // If this is an expr used in a stmt context, indent and newline it.
88
7.33k
        Indent();
89
7.33k
        Visit(S);
90
7.33k
        OS << ";" << NL;
91
29.5k
      } else if (S) {
92
29.5k
        Visit(S);
93
29.5k
      } else {
94
0
        Indent() << "<<<NULL STATEMENT>>>" << NL;
95
0
      }
96
36.8k
      IndentLevel -= SubIndent;
97
36.8k
    }
98
99
6.86k
    void PrintInitStmt(Stmt *S, unsigned PrefixWidth) {
100
      // FIXME: Cope better with odd prefix widths.
101
6.86k
      IndentLevel += (PrefixWidth + 1) / 2;
102
6.86k
      if (auto *DS = dyn_cast<DeclStmt>(S))
103
6.77k
        PrintRawDeclStmt(DS);
104
84
      else
105
84
        PrintExpr(cast<Expr>(S));
106
6.86k
      OS << "; ";
107
6.86k
      IndentLevel -= (PrefixWidth + 1) / 2;
108
6.86k
    }
109
110
6.91k
    void PrintControlledStmt(Stmt *S) {
111
6.91k
      if (auto *CS = dyn_cast<CompoundStmt>(S)) {
112
1.23k
        OS << " ";
113
1.23k
        PrintRawCompoundStmt(CS);
114
1.23k
        OS << NL;
115
5.67k
      } else {
116
5.67k
        OS << NL;
117
5.67k
        PrintStmt(S);
118
5.67k
      }
119
6.91k
    }
120
121
    void PrintRawCompoundStmt(CompoundStmt *S);
122
    void PrintRawDecl(Decl *D);
123
    void PrintRawDeclStmt(const DeclStmt *S);
124
    void PrintRawIfStmt(IfStmt *If);
125
    void PrintRawCXXCatchStmt(CXXCatchStmt *Catch);
126
    void PrintCallArgs(CallExpr *E);
127
    void PrintRawSEHExceptHandler(SEHExceptStmt *S);
128
    void PrintRawSEHFinallyStmt(SEHFinallyStmt *S);
129
    void PrintOMPExecutableDirective(OMPExecutableDirective *S,
130
                                     bool ForceNoStmt = false);
131
132
160k
    void PrintExpr(Expr *E) {
133
160k
      if (E)
134
160k
        Visit(E);
135
0
      else
136
0
        OS << "<null expr>";
137
160k
    }
138
139
50.3k
    raw_ostream &Indent(int Delta = 0) {
140
241k
      for (int i = 0, e = IndentLevel+Delta; i < e; 
++i191k
)
141
191k
        OS << "  ";
142
50.3k
      return OS;
143
50.3k
    }
144
145
309k
    void Visit(Stmt* S) {
146
309k
      if (Helper && 
Helper->handledStmt(S,OS)92.5k
)
147
51.9k
          return;
148
258k
      else StmtVisitor<StmtPrinter>::Visit(S);
149
309k
    }
150
151
0
    void VisitStmt(Stmt *Node) LLVM_ATTRIBUTE_UNUSED {
152
0
      Indent() << "<<unknown stmt type>>" << NL;
153
0
    }
154
155
0
    void VisitExpr(Expr *Node) LLVM_ATTRIBUTE_UNUSED {
156
0
      OS << "<<unknown expr type>>";
157
0
    }
158
159
    void VisitCXXNamedCastExpr(CXXNamedCastExpr *Node);
160
161
#define ABSTRACT_STMT(CLASS)
162
#define STMT(CLASS, PARENT) \
163
    void Visit##CLASS(CLASS *Node);
164
#include "clang/AST/StmtNodes.inc"
165
  };
166
167
} // namespace
168
169
//===----------------------------------------------------------------------===//
170
//  Stmt printing methods.
171
//===----------------------------------------------------------------------===//
172
173
/// PrintRawCompoundStmt - Print a compound stmt without indenting the {, and
174
/// with no newline after the }.
175
7.29k
void StmtPrinter::PrintRawCompoundStmt(CompoundStmt *Node) {
176
7.29k
  OS << "{" << NL;
177
7.29k
  for (auto *I : Node->body())
178
21.2k
    PrintStmt(I);
179
180
7.29k
  Indent() << "}";
181
7.29k
}
182
183
31
void StmtPrinter::PrintRawDecl(Decl *D) {
184
31
  D->print(OS, Policy, IndentLevel);
185
31
}
186
187
14.0k
void StmtPrinter::PrintRawDeclStmt(const DeclStmt *S) {
188
14.0k
  SmallVector<Decl *, 2> Decls(S->decls());
189
14.0k
  Decl::printGroup(Decls.data(), Decls.size(), OS, Policy, IndentLevel);
190
14.0k
}
191
192
592
void StmtPrinter::VisitNullStmt(NullStmt *Node) {
193
592
  Indent() << ";" << NL;
194
592
}
195
196
7.27k
void StmtPrinter::VisitDeclStmt(DeclStmt *Node) {
197
7.27k
  Indent();
198
7.27k
  PrintRawDeclStmt(Node);
199
7.27k
  OS << ";" << NL;
200
7.27k
}
201
202
5.87k
void StmtPrinter::VisitCompoundStmt(CompoundStmt *Node) {
203
5.87k
  Indent();
204
5.87k
  PrintRawCompoundStmt(Node);
205
5.87k
  OS << "" << NL;
206
5.87k
}
207
208
32
void StmtPrinter::VisitCaseStmt(CaseStmt *Node) {
209
32
  Indent(-1) << "case ";
210
32
  PrintExpr(Node->getLHS());
211
32
  if (Node->getRHS()) {
212
2
    OS << " ... ";
213
2
    PrintExpr(Node->getRHS());
214
2
  }
215
32
  OS << ":" << NL;
216
217
32
  PrintStmt(Node->getSubStmt(), 0);
218
32
}
219
220
18
void StmtPrinter::VisitDefaultStmt(DefaultStmt *Node) {
221
18
  Indent(-1) << "default:" << NL;
222
18
  PrintStmt(Node->getSubStmt(), 0);
223
18
}
224
225
8
void StmtPrinter::VisitLabelStmt(LabelStmt *Node) {
226
8
  Indent(-1) << Node->getName() << ":" << NL;
227
8
  PrintStmt(Node->getSubStmt(), 0);
228
8
}
229
230
26
void StmtPrinter::VisitAttributedStmt(AttributedStmt *Node) {
231
55
  for (const auto *Attr : Node->getAttrs()) {
232
55
    Attr->printPretty(OS, Policy);
233
55
  }
234
235
26
  PrintStmt(Node->getSubStmt(), 0);
236
26
}
237
238
28
void StmtPrinter::PrintRawIfStmt(IfStmt *If) {
239
28
  OS << "if (";
240
28
  if (If->getInit())
241
0
    PrintInitStmt(If->getInit(), 4);
242
28
  if (const DeclStmt *DS = If->getConditionVariableDeclStmt())
243
1
    PrintRawDeclStmt(DS);
244
27
  else
245
27
    PrintExpr(If->getCond());
246
28
  OS << ')';
247
248
28
  if (auto *CS = dyn_cast<CompoundStmt>(If->getThen())) {
249
5
    OS << ' ';
250
5
    PrintRawCompoundStmt(CS);
251
5
    OS << (If->getElse() ? 
" "4
:
NL1
);
252
23
  } else {
253
23
    OS << NL;
254
23
    PrintStmt(If->getThen());
255
23
    if (If->getElse()) 
Indent()0
;
256
23
  }
257
258
28
  if (Stmt *Else = If->getElse()) {
259
4
    OS << "else";
260
261
4
    if (auto *CS = dyn_cast<CompoundStmt>(Else)) {
262
2
      OS << ' ';
263
2
      PrintRawCompoundStmt(CS);
264
2
      OS << NL;
265
2
    } else if (auto *ElseIf = dyn_cast<IfStmt>(Else)) {
266
2
      OS << ' ';
267
2
      PrintRawIfStmt(ElseIf);
268
2
    } else {
269
0
      OS << NL;
270
0
      PrintStmt(If->getElse());
271
0
    }
272
4
  }
273
28
}
274
275
26
void StmtPrinter::VisitIfStmt(IfStmt *If) {
276
26
  Indent();
277
26
  PrintRawIfStmt(If);
278
26
}
279
280
26
void StmtPrinter::VisitSwitchStmt(SwitchStmt *Node) {
281
26
  Indent() << "switch (";
282
26
  if (Node->getInit())
283
0
    PrintInitStmt(Node->getInit(), 8);
284
26
  if (const DeclStmt *DS = Node->getConditionVariableDeclStmt())
285
1
    PrintRawDeclStmt(DS);
286
25
  else
287
25
    PrintExpr(Node->getCond());
288
26
  OS << ")";
289
26
  PrintControlledStmt(Node->getBody());
290
26
}
291
292
22
void StmtPrinter::VisitWhileStmt(WhileStmt *Node) {
293
22
  Indent() << "while (";
294
22
  if (const DeclStmt *DS = Node->getConditionVariableDeclStmt())
295
1
    PrintRawDeclStmt(DS);
296
21
  else
297
21
    PrintExpr(Node->getCond());
298
22
  OS << ")" << NL;
299
22
  PrintStmt(Node->getBody());
300
22
}
301
302
2
void StmtPrinter::VisitDoStmt(DoStmt *Node) {
303
2
  Indent() << "do ";
304
2
  if (auto *CS = dyn_cast<CompoundStmt>(Node->getBody())) {
305
2
    PrintRawCompoundStmt(CS);
306
2
    OS << " ";
307
2
  } else {
308
0
    OS << NL;
309
0
    PrintStmt(Node->getBody());
310
0
    Indent();
311
0
  }
312
313
2
  OS << "while (";
314
2
  PrintExpr(Node->getCond());
315
2
  OS << ");" << NL;
316
2
}
317
318
6.86k
void StmtPrinter::VisitForStmt(ForStmt *Node) {
319
6.86k
  Indent() << "for (";
320
6.86k
  if (Node->getInit())
321
6.85k
    PrintInitStmt(Node->getInit(), 5);
322
2
  else
323
2
    OS << (Node->getCond() ? 
"; "0
: ";");
324
6.86k
  if (Node->getCond())
325
6.85k
    PrintExpr(Node->getCond());
326
6.86k
  OS << ";";
327
6.86k
  if (Node->getInc()) {
328
6.85k
    OS << " ";
329
6.85k
    PrintExpr(Node->getInc());
330
6.85k
  }
331
6.86k
  OS << ")";
332
6.86k
  PrintControlledStmt(Node->getBody());
333
6.86k
}
334
335
1
void StmtPrinter::VisitObjCForCollectionStmt(ObjCForCollectionStmt *Node) {
336
1
  Indent() << "for (";
337
1
  if (auto *DS = dyn_cast<DeclStmt>(Node->getElement()))
338
1
    PrintRawDeclStmt(DS);
339
0
  else
340
0
    PrintExpr(cast<Expr>(Node->getElement()));
341
1
  OS << " in ";
342
1
  PrintExpr(Node->getCollection());
343
1
  OS << ")";
344
1
  PrintControlledStmt(Node->getBody());
345
1
}
346
347
29
void StmtPrinter::VisitCXXForRangeStmt(CXXForRangeStmt *Node) {
348
29
  Indent() << "for (";
349
29
  if (Node->getInit())
350
1
    PrintInitStmt(Node->getInit(), 5);
351
29
  PrintingPolicy SubPolicy(Policy);
352
29
  SubPolicy.SuppressInitializers = true;
353
29
  Node->getLoopVariable()->print(OS, SubPolicy, IndentLevel);
354
29
  OS << " : ";
355
29
  PrintExpr(Node->getRangeInit());
356
29
  OS << ")";
357
29
  PrintControlledStmt(Node->getBody());
358
29
}
359
360
0
void StmtPrinter::VisitMSDependentExistsStmt(MSDependentExistsStmt *Node) {
361
0
  Indent();
362
0
  if (Node->isIfExists())
363
0
    OS << "__if_exists (";
364
0
  else
365
0
    OS << "__if_not_exists (";
366
367
0
  if (NestedNameSpecifier *Qualifier
368
0
        = Node->getQualifierLoc().getNestedNameSpecifier())
369
0
    Qualifier->print(OS, Policy);
370
371
0
  OS << Node->getNameInfo() << ") ";
372
373
0
  PrintRawCompoundStmt(Node->getSubStmt());
374
0
}
375
376
19
void StmtPrinter::VisitGotoStmt(GotoStmt *Node) {
377
19
  Indent() << "goto " << Node->getLabel()->getName() << ";";
378
19
  if (Policy.IncludeNewlines) 
OS << NL6
;
379
19
}
380
381
2
void StmtPrinter::VisitIndirectGotoStmt(IndirectGotoStmt *Node) {
382
2
  Indent() << "goto *";
383
2
  PrintExpr(Node->getTarget());
384
2
  OS << ";";
385
2
  if (Policy.IncludeNewlines) OS << NL;
386
2
}
387
388
21
void StmtPrinter::VisitContinueStmt(ContinueStmt *Node) {
389
21
  Indent() << "continue;";
390
21
  if (Policy.IncludeNewlines) 
OS << NL2
;
391
21
}
392
393
116
void StmtPrinter::VisitBreakStmt(BreakStmt *Node) {
394
116
  Indent() << "break;";
395
116
  if (Policy.IncludeNewlines) 
OS << NL45
;
396
116
}
397
398
2.28k
void StmtPrinter::VisitReturnStmt(ReturnStmt *Node) {
399
2.28k
  Indent() << "return";
400
2.28k
  if (Node->getRetValue()) {
401
2.20k
    OS << " ";
402
2.20k
    PrintExpr(Node->getRetValue());
403
2.20k
  }
404
2.28k
  OS << ";";
405
2.28k
  if (Policy.IncludeNewlines) OS << NL;
406
2.28k
}
407
408
13
void StmtPrinter::VisitGCCAsmStmt(GCCAsmStmt *Node) {
409
13
  Indent() << "asm ";
410
411
13
  if (Node->isVolatile())
412
1
    OS << "volatile ";
413
414
13
  if (Node->isAsmGoto())
415
8
    OS << "goto ";
416
417
13
  OS << "(";
418
13
  VisitStringLiteral(Node->getAsmString());
419
420
  // Outputs
421
13
  if (Node->getNumOutputs() != 0 || 
Node->getNumInputs() != 010
||
422
13
      
Node->getNumClobbers() != 04
||
Node->getNumLabels() != 04
)
423
11
    OS << " : ";
424
425
16
  for (unsigned i = 0, e = Node->getNumOutputs(); i != e; 
++i3
) {
426
3
    if (i != 0)
427
0
      OS << ", ";
428
429
3
    if (!Node->getOutputName(i).empty()) {
430
0
      OS << '[';
431
0
      OS << Node->getOutputName(i);
432
0
      OS << "] ";
433
0
    }
434
435
3
    VisitStringLiteral(Node->getOutputConstraintLiteral(i));
436
3
    OS << " (";
437
3
    Visit(Node->getOutputExpr(i));
438
3
    OS << ")";
439
3
  }
440
441
  // Inputs
442
13
  if (Node->getNumInputs() != 0 || 
Node->getNumClobbers() != 06
||
443
13
      
Node->getNumLabels() != 06
)
444
9
    OS << " : ";
445
446
21
  for (unsigned i = 0, e = Node->getNumInputs(); i != e; 
++i8
) {
447
8
    if (i != 0)
448
1
      OS << ", ";
449
450
8
    if (!Node->getInputName(i).empty()) {
451
0
      OS << '[';
452
0
      OS << Node->getInputName(i);
453
0
      OS << "] ";
454
0
    }
455
456
8
    VisitStringLiteral(Node->getInputConstraintLiteral(i));
457
8
    OS << " (";
458
8
    Visit(Node->getInputExpr(i));
459
8
    OS << ")";
460
8
  }
461
462
  // Clobbers
463
13
  if (Node->getNumClobbers() != 0 || Node->getNumLabels())
464
8
    OS << " : ";
465
466
13
  for (unsigned i = 0, e = Node->getNumClobbers(); i != e; 
++i0
) {
467
0
    if (i != 0)
468
0
      OS << ", ";
469
470
0
    VisitStringLiteral(Node->getClobberStringLiteral(i));
471
0
  }
472
473
  // Labels
474
13
  if (Node->getNumLabels() != 0)
475
8
    OS << " : ";
476
477
33
  for (unsigned i = 0, e = Node->getNumLabels(); i != e; 
++i20
) {
478
20
    if (i != 0)
479
12
      OS << ", ";
480
20
    OS << Node->getLabelName(i);
481
20
  }
482
483
13
  OS << ");";
484
13
  if (Policy.IncludeNewlines) 
OS << NL7
;
485
13
}
486
487
0
void StmtPrinter::VisitMSAsmStmt(MSAsmStmt *Node) {
488
  // FIXME: Implement MS style inline asm statement printer.
489
0
  Indent() << "__asm ";
490
0
  if (Node->hasBraces())
491
0
    OS << "{" << NL;
492
0
  OS << Node->getAsmString() << NL;
493
0
  if (Node->hasBraces())
494
0
    Indent() << "}" << NL;
495
0
}
496
497
0
void StmtPrinter::VisitCapturedStmt(CapturedStmt *Node) {
498
0
  PrintStmt(Node->getCapturedDecl()->getBody());
499
0
}
500
501
3
void StmtPrinter::VisitObjCAtTryStmt(ObjCAtTryStmt *Node) {
502
3
  Indent() << "@try";
503
3
  if (auto *TS = dyn_cast<CompoundStmt>(Node->getTryBody())) {
504
3
    PrintRawCompoundStmt(TS);
505
3
    OS << NL;
506
3
  }
507
508
11
  for (unsigned I = 0, N = Node->getNumCatchStmts(); I != N; 
++I8
) {
509
8
    ObjCAtCatchStmt *catchStmt = Node->getCatchStmt(I);
510
8
    Indent() << "@catch(";
511
8
    if (catchStmt->getCatchParamDecl()) {
512
6
      if (Decl *DS = catchStmt->getCatchParamDecl())
513
6
        PrintRawDecl(DS);
514
6
    }
515
8
    OS << ")";
516
8
    if (auto *CS = dyn_cast<CompoundStmt>(catchStmt->getCatchBody())) {
517
8
      PrintRawCompoundStmt(CS);
518
8
      OS << NL;
519
8
    }
520
8
  }
521
522
3
  if (auto *FS = static_cast<ObjCAtFinallyStmt *>(Node->getFinallyStmt())) {
523
3
    Indent() << "@finally";
524
3
    PrintRawCompoundStmt(dyn_cast<CompoundStmt>(FS->getFinallyBody()));
525
3
    OS << NL;
526
3
  }
527
3
}
528
529
0
void StmtPrinter::VisitObjCAtFinallyStmt(ObjCAtFinallyStmt *Node) {
530
0
}
531
532
0
void StmtPrinter::VisitObjCAtCatchStmt (ObjCAtCatchStmt *Node) {
533
0
  Indent() << "@catch (...) { /* todo */ } " << NL;
534
0
}
535
536
2
void StmtPrinter::VisitObjCAtThrowStmt(ObjCAtThrowStmt *Node) {
537
2
  Indent() << "@throw";
538
2
  if (Node->getThrowExpr()) {
539
1
    OS << " ";
540
1
    PrintExpr(Node->getThrowExpr());
541
1
  }
542
2
  OS << ";" << NL;
543
2
}
544
545
void StmtPrinter::VisitObjCAvailabilityCheckExpr(
546
0
    ObjCAvailabilityCheckExpr *Node) {
547
0
  OS << "@available(...)";
548
0
}
549
550
1
void StmtPrinter::VisitObjCAtSynchronizedStmt(ObjCAtSynchronizedStmt *Node) {
551
1
  Indent() << "@synchronized (";
552
1
  PrintExpr(Node->getSynchExpr());
553
1
  OS << ")";
554
1
  PrintRawCompoundStmt(Node->getSynchBody());
555
1
  OS << NL;
556
1
}
557
558
0
void StmtPrinter::VisitObjCAutoreleasePoolStmt(ObjCAutoreleasePoolStmt *Node) {
559
0
  Indent() << "@autoreleasepool";
560
0
  PrintRawCompoundStmt(dyn_cast<CompoundStmt>(Node->getSubStmt()));
561
0
  OS << NL;
562
0
}
563
564
8
void StmtPrinter::PrintRawCXXCatchStmt(CXXCatchStmt *Node) {
565
8
  OS << "catch (";
566
8
  if (Decl *ExDecl = Node->getExceptionDecl())
567
8
    PrintRawDecl(ExDecl);
568
0
  else
569
0
    OS << "...";
570
8
  OS << ") ";
571
8
  PrintRawCompoundStmt(cast<CompoundStmt>(Node->getHandlerBlock()));
572
8
}
573
574
8
void StmtPrinter::VisitCXXCatchStmt(CXXCatchStmt *Node) {
575
8
  Indent();
576
8
  PrintRawCXXCatchStmt(Node);
577
8
  OS << NL;
578
8
}
579
580
0
void StmtPrinter::VisitCXXTryStmt(CXXTryStmt *Node) {
581
0
  Indent() << "try ";
582
0
  PrintRawCompoundStmt(Node->getTryBlock());
583
0
  for (unsigned i = 0, e = Node->getNumHandlers(); i < e; ++i) {
584
0
    OS << " ";
585
0
    PrintRawCXXCatchStmt(Node->getHandler(i));
586
0
  }
587
0
  OS << NL;
588
0
}
589
590
0
void StmtPrinter::VisitSEHTryStmt(SEHTryStmt *Node) {
591
0
  Indent() << (Node->getIsCXXTry() ? "try " : "__try ");
592
0
  PrintRawCompoundStmt(Node->getTryBlock());
593
0
  SEHExceptStmt *E = Node->getExceptHandler();
594
0
  SEHFinallyStmt *F = Node->getFinallyHandler();
595
0
  if(E)
596
0
    PrintRawSEHExceptHandler(E);
597
0
  else {
598
0
    assert(F && "Must have a finally block...");
599
0
    PrintRawSEHFinallyStmt(F);
600
0
  }
601
0
  OS << NL;
602
0
}
603
604
0
void StmtPrinter::PrintRawSEHFinallyStmt(SEHFinallyStmt *Node) {
605
0
  OS << "__finally ";
606
0
  PrintRawCompoundStmt(Node->getBlock());
607
0
  OS << NL;
608
0
}
609
610
0
void StmtPrinter::PrintRawSEHExceptHandler(SEHExceptStmt *Node) {
611
0
  OS << "__except (";
612
0
  VisitExpr(Node->getFilterExpr());
613
0
  OS << ")" << NL;
614
0
  PrintRawCompoundStmt(Node->getBlock());
615
0
  OS << NL;
616
0
}
617
618
0
void StmtPrinter::VisitSEHExceptStmt(SEHExceptStmt *Node) {
619
0
  Indent();
620
0
  PrintRawSEHExceptHandler(Node);
621
0
  OS << NL;
622
0
}
623
624
0
void StmtPrinter::VisitSEHFinallyStmt(SEHFinallyStmt *Node) {
625
0
  Indent();
626
0
  PrintRawSEHFinallyStmt(Node);
627
0
  OS << NL;
628
0
}
629
630
0
void StmtPrinter::VisitSEHLeaveStmt(SEHLeaveStmt *Node) {
631
0
  Indent() << "__leave;";
632
0
  if (Policy.IncludeNewlines) OS << NL;
633
0
}
634
635
//===----------------------------------------------------------------------===//
636
//  OpenMP directives printing methods
637
//===----------------------------------------------------------------------===//
638
639
0
void StmtPrinter::VisitOMPCanonicalLoop(OMPCanonicalLoop *Node) {
640
0
  PrintStmt(Node->getLoopStmt());
641
0
}
642
643
void StmtPrinter::PrintOMPExecutableDirective(OMPExecutableDirective *S,
644
12.5k
                                              bool ForceNoStmt) {
645
12.5k
  OMPClausePrinter Printer(OS, Policy);
646
12.5k
  ArrayRef<OMPClause *> Clauses = S->clauses();
647
12.5k
  for (auto *Clause : Clauses)
648
26.5k
    if (Clause && !Clause->isImplicit()) {
649
25.5k
      OS << ' ';
650
25.5k
      Printer.Visit(Clause);
651
25.5k
    }
652
12.5k
  OS << NL;
653
12.5k
  if (!ForceNoStmt && 
S->hasAssociatedStmt()10.1k
)
654
9.74k
    PrintStmt(S->getRawStmt());
655
12.5k
}
656
657
569
void StmtPrinter::VisitOMPParallelDirective(OMPParallelDirective *Node) {
658
569
  Indent() << "#pragma omp parallel";
659
569
  PrintOMPExecutableDirective(Node);
660
569
}
661
662
117
void StmtPrinter::VisitOMPSimdDirective(OMPSimdDirective *Node) {
663
117
  Indent() << "#pragma omp simd";
664
117
  PrintOMPExecutableDirective(Node);
665
117
}
666
667
14
void StmtPrinter::VisitOMPTileDirective(OMPTileDirective *Node) {
668
14
  Indent() << "#pragma omp tile";
669
14
  PrintOMPExecutableDirective(Node);
670
14
}
671
672
14
void StmtPrinter::VisitOMPUnrollDirective(OMPUnrollDirective *Node) {
673
14
  Indent() << "#pragma omp unroll";
674
14
  PrintOMPExecutableDirective(Node);
675
14
}
676
677
294
void StmtPrinter::VisitOMPForDirective(OMPForDirective *Node) {
678
294
  Indent() << "#pragma omp for";
679
294
  PrintOMPExecutableDirective(Node);
680
294
}
681
682
121
void StmtPrinter::VisitOMPForSimdDirective(OMPForSimdDirective *Node) {
683
121
  Indent() << "#pragma omp for simd";
684
121
  PrintOMPExecutableDirective(Node);
685
121
}
686
687
28
void StmtPrinter::VisitOMPSectionsDirective(OMPSectionsDirective *Node) {
688
28
  Indent() << "#pragma omp sections";
689
28
  PrintOMPExecutableDirective(Node);
690
28
}
691
692
28
void StmtPrinter::VisitOMPSectionDirective(OMPSectionDirective *Node) {
693
28
  Indent() << "#pragma omp section";
694
28
  PrintOMPExecutableDirective(Node);
695
28
}
696
697
49
void StmtPrinter::VisitOMPSingleDirective(OMPSingleDirective *Node) {
698
49
  Indent() << "#pragma omp single";
699
49
  PrintOMPExecutableDirective(Node);
700
49
}
701
702
5
void StmtPrinter::VisitOMPMasterDirective(OMPMasterDirective *Node) {
703
5
  Indent() << "#pragma omp master";
704
5
  PrintOMPExecutableDirective(Node);
705
5
}
706
707
33
void StmtPrinter::VisitOMPCriticalDirective(OMPCriticalDirective *Node) {
708
33
  Indent() << "#pragma omp critical";
709
33
  if (Node->getDirectiveName().getName()) {
710
12
    OS << " (";
711
12
    Node->getDirectiveName().printName(OS, Policy);
712
12
    OS << ")";
713
12
  }
714
33
  PrintOMPExecutableDirective(Node);
715
33
}
716
717
77
void StmtPrinter::VisitOMPParallelForDirective(OMPParallelForDirective *Node) {
718
77
  Indent() << "#pragma omp parallel for";
719
77
  PrintOMPExecutableDirective(Node);
720
77
}
721
722
void StmtPrinter::VisitOMPParallelForSimdDirective(
723
117
    OMPParallelForSimdDirective *Node) {
724
117
  Indent() << "#pragma omp parallel for simd";
725
117
  PrintOMPExecutableDirective(Node);
726
117
}
727
728
void StmtPrinter::VisitOMPParallelMasterDirective(
729
128
    OMPParallelMasterDirective *Node) {
730
128
  Indent() << "#pragma omp parallel master";
731
128
  PrintOMPExecutableDirective(Node);
732
128
}
733
734
void StmtPrinter::VisitOMPParallelSectionsDirective(
735
45
    OMPParallelSectionsDirective *Node) {
736
45
  Indent() << "#pragma omp parallel sections";
737
45
  PrintOMPExecutableDirective(Node);
738
45
}
739
740
85
void StmtPrinter::VisitOMPTaskDirective(OMPTaskDirective *Node) {
741
85
  Indent() << "#pragma omp task";
742
85
  PrintOMPExecutableDirective(Node);
743
85
}
744
745
16
void StmtPrinter::VisitOMPTaskyieldDirective(OMPTaskyieldDirective *Node) {
746
16
  Indent() << "#pragma omp taskyield";
747
16
  PrintOMPExecutableDirective(Node);
748
16
}
749
750
64
void StmtPrinter::VisitOMPBarrierDirective(OMPBarrierDirective *Node) {
751
64
  Indent() << "#pragma omp barrier";
752
64
  PrintOMPExecutableDirective(Node);
753
64
}
754
755
16
void StmtPrinter::VisitOMPTaskwaitDirective(OMPTaskwaitDirective *Node) {
756
16
  Indent() << "#pragma omp taskwait";
757
16
  PrintOMPExecutableDirective(Node);
758
16
}
759
760
201
void StmtPrinter::VisitOMPTaskgroupDirective(OMPTaskgroupDirective *Node) {
761
201
  Indent() << "#pragma omp taskgroup";
762
201
  PrintOMPExecutableDirective(Node);
763
201
}
764
765
80
void StmtPrinter::VisitOMPFlushDirective(OMPFlushDirective *Node) {
766
80
  Indent() << "#pragma omp flush";
767
80
  PrintOMPExecutableDirective(Node);
768
80
}
769
770
44
void StmtPrinter::VisitOMPDepobjDirective(OMPDepobjDirective *Node) {
771
44
  Indent() << "#pragma omp depobj";
772
44
  PrintOMPExecutableDirective(Node);
773
44
}
774
775
16
void StmtPrinter::VisitOMPScanDirective(OMPScanDirective *Node) {
776
16
  Indent() << "#pragma omp scan";
777
16
  PrintOMPExecutableDirective(Node);
778
16
}
779
780
85
void StmtPrinter::VisitOMPOrderedDirective(OMPOrderedDirective *Node) {
781
85
  Indent() << "#pragma omp ordered";
782
85
  PrintOMPExecutableDirective(Node, Node->hasClausesOfKind<OMPDependClause>());
783
85
}
784
785
505
void StmtPrinter::VisitOMPAtomicDirective(OMPAtomicDirective *Node) {
786
505
  Indent() << "#pragma omp atomic";
787
505
  PrintOMPExecutableDirective(Node);
788
505
}
789
790
2.35k
void StmtPrinter::VisitOMPTargetDirective(OMPTargetDirective *Node) {
791
2.35k
  Indent() << "#pragma omp target";
792
2.35k
  PrintOMPExecutableDirective(Node);
793
2.35k
}
794
795
384
void StmtPrinter::VisitOMPTargetDataDirective(OMPTargetDataDirective *Node) {
796
384
  Indent() << "#pragma omp target data";
797
384
  PrintOMPExecutableDirective(Node);
798
384
}
799
800
void StmtPrinter::VisitOMPTargetEnterDataDirective(
801
768
    OMPTargetEnterDataDirective *Node) {
802
768
  Indent() << "#pragma omp target enter data";
803
768
  PrintOMPExecutableDirective(Node, /*ForceNoStmt=*/true);
804
768
}
805
806
void StmtPrinter::VisitOMPTargetExitDataDirective(
807
832
    OMPTargetExitDataDirective *Node) {
808
832
  Indent() << "#pragma omp target exit data";
809
832
  PrintOMPExecutableDirective(Node, /*ForceNoStmt=*/true);
810
832
}
811
812
void StmtPrinter::VisitOMPTargetParallelDirective(
813
345
    OMPTargetParallelDirective *Node) {
814
345
  Indent() << "#pragma omp target parallel";
815
345
  PrintOMPExecutableDirective(Node);
816
345
}
817
818
void StmtPrinter::VisitOMPTargetParallelForDirective(
819
385
    OMPTargetParallelForDirective *Node) {
820
385
  Indent() << "#pragma omp target parallel for";
821
385
  PrintOMPExecutableDirective(Node);
822
385
}
823
824
477
void StmtPrinter::VisitOMPTeamsDirective(OMPTeamsDirective *Node) {
825
477
  Indent() << "#pragma omp teams";
826
477
  PrintOMPExecutableDirective(Node);
827
477
}
828
829
void StmtPrinter::VisitOMPCancellationPointDirective(
830
68
    OMPCancellationPointDirective *Node) {
831
68
  Indent() << "#pragma omp cancellation point "
832
68
           << getOpenMPDirectiveName(Node->getCancelRegion());
833
68
  PrintOMPExecutableDirective(Node);
834
68
}
835
836
92
void StmtPrinter::VisitOMPCancelDirective(OMPCancelDirective *Node) {
837
92
  Indent() << "#pragma omp cancel "
838
92
           << getOpenMPDirectiveName(Node->getCancelRegion());
839
92
  PrintOMPExecutableDirective(Node);
840
92
}
841
842
33
void StmtPrinter::VisitOMPTaskLoopDirective(OMPTaskLoopDirective *Node) {
843
33
  Indent() << "#pragma omp taskloop";
844
33
  PrintOMPExecutableDirective(Node);
845
33
}
846
847
void StmtPrinter::VisitOMPTaskLoopSimdDirective(
848
65
    OMPTaskLoopSimdDirective *Node) {
849
65
  Indent() << "#pragma omp taskloop simd";
850
65
  PrintOMPExecutableDirective(Node);
851
65
}
852
853
void StmtPrinter::VisitOMPMasterTaskLoopDirective(
854
32
    OMPMasterTaskLoopDirective *Node) {
855
32
  Indent() << "#pragma omp master taskloop";
856
32
  PrintOMPExecutableDirective(Node);
857
32
}
858
859
void StmtPrinter::VisitOMPMasterTaskLoopSimdDirective(
860
64
    OMPMasterTaskLoopSimdDirective *Node) {
861
64
  Indent() << "#pragma omp master taskloop simd";
862
64
  PrintOMPExecutableDirective(Node);
863
64
}
864
865
void StmtPrinter::VisitOMPParallelMasterTaskLoopDirective(
866
32
    OMPParallelMasterTaskLoopDirective *Node) {
867
32
  Indent() << "#pragma omp parallel master taskloop";
868
32
  PrintOMPExecutableDirective(Node);
869
32
}
870
871
void StmtPrinter::VisitOMPParallelMasterTaskLoopSimdDirective(
872
64
    OMPParallelMasterTaskLoopSimdDirective *Node) {
873
64
  Indent() << "#pragma omp parallel master taskloop simd";
874
64
  PrintOMPExecutableDirective(Node);
875
64
}
876
877
124
void StmtPrinter::VisitOMPDistributeDirective(OMPDistributeDirective *Node) {
878
124
  Indent() << "#pragma omp distribute";
879
124
  PrintOMPExecutableDirective(Node);
880
124
}
881
882
void StmtPrinter::VisitOMPTargetUpdateDirective(
883
689
    OMPTargetUpdateDirective *Node) {
884
689
  Indent() << "#pragma omp target update";
885
689
  PrintOMPExecutableDirective(Node, /*ForceNoStmt=*/true);
886
689
}
887
888
void StmtPrinter::VisitOMPDistributeParallelForDirective(
889
121
    OMPDistributeParallelForDirective *Node) {
890
121
  Indent() << "#pragma omp distribute parallel for";
891
121
  PrintOMPExecutableDirective(Node);
892
121
}
893
894
void StmtPrinter::VisitOMPDistributeParallelForSimdDirective(
895
113
    OMPDistributeParallelForSimdDirective *Node) {
896
113
  Indent() << "#pragma omp distribute parallel for simd";
897
113
  PrintOMPExecutableDirective(Node);
898
113
}
899
900
void StmtPrinter::VisitOMPDistributeSimdDirective(
901
113
    OMPDistributeSimdDirective *Node) {
902
113
  Indent() << "#pragma omp distribute simd";
903
113
  PrintOMPExecutableDirective(Node);
904
113
}
905
906
void StmtPrinter::VisitOMPTargetParallelForSimdDirective(
907
589
    OMPTargetParallelForSimdDirective *Node) {
908
589
  Indent() << "#pragma omp target parallel for simd";
909
589
  PrintOMPExecutableDirective(Node);
910
589
}
911
912
449
void StmtPrinter::VisitOMPTargetSimdDirective(OMPTargetSimdDirective *Node) {
913
449
  Indent() << "#pragma omp target simd";
914
449
  PrintOMPExecutableDirective(Node);
915
449
}
916
917
void StmtPrinter::VisitOMPTeamsDistributeDirective(
918
60
    OMPTeamsDistributeDirective *Node) {
919
60
  Indent() << "#pragma omp teams distribute";
920
60
  PrintOMPExecutableDirective(Node);
921
60
}
922
923
void StmtPrinter::VisitOMPTeamsDistributeSimdDirective(
924
169
    OMPTeamsDistributeSimdDirective *Node) {
925
169
  Indent() << "#pragma omp teams distribute simd";
926
169
  PrintOMPExecutableDirective(Node);
927
169
}
928
929
void StmtPrinter::VisitOMPTeamsDistributeParallelForSimdDirective(
930
169
    OMPTeamsDistributeParallelForSimdDirective *Node) {
931
169
  Indent() << "#pragma omp teams distribute parallel for simd";
932
169
  PrintOMPExecutableDirective(Node);
933
169
}
934
935
void StmtPrinter::VisitOMPTeamsDistributeParallelForDirective(
936
69
    OMPTeamsDistributeParallelForDirective *Node) {
937
69
  Indent() << "#pragma omp teams distribute parallel for";
938
69
  PrintOMPExecutableDirective(Node);
939
69
}
940
941
185
void StmtPrinter::VisitOMPTargetTeamsDirective(OMPTargetTeamsDirective *Node) {
942
185
  Indent() << "#pragma omp target teams";
943
185
  PrintOMPExecutableDirective(Node);
944
185
}
945
946
void StmtPrinter::VisitOMPTargetTeamsDistributeDirective(
947
61
    OMPTargetTeamsDistributeDirective *Node) {
948
61
  Indent() << "#pragma omp target teams distribute";
949
61
  PrintOMPExecutableDirective(Node);
950
61
}
951
952
void StmtPrinter::VisitOMPTargetTeamsDistributeParallelForDirective(
953
209
    OMPTargetTeamsDistributeParallelForDirective *Node) {
954
209
  Indent() << "#pragma omp target teams distribute parallel for";
955
209
  PrintOMPExecutableDirective(Node);
956
209
}
957
958
void StmtPrinter::VisitOMPTargetTeamsDistributeParallelForSimdDirective(
959
225
    OMPTargetTeamsDistributeParallelForSimdDirective *Node) {
960
225
  Indent() << "#pragma omp target teams distribute parallel for simd";
961
225
  PrintOMPExecutableDirective(Node);
962
225
}
963
964
void StmtPrinter::VisitOMPTargetTeamsDistributeSimdDirective(
965
309
    OMPTargetTeamsDistributeSimdDirective *Node) {
966
309
  Indent() << "#pragma omp target teams distribute simd";
967
309
  PrintOMPExecutableDirective(Node);
968
309
}
969
970
56
void StmtPrinter::VisitOMPInteropDirective(OMPInteropDirective *Node) {
971
56
  Indent() << "#pragma omp interop";
972
56
  PrintOMPExecutableDirective(Node);
973
56
}
974
975
42
void StmtPrinter::VisitOMPDispatchDirective(OMPDispatchDirective *Node) {
976
42
  Indent() << "#pragma omp dispatch";
977
42
  PrintOMPExecutableDirective(Node);
978
42
}
979
980
12
void StmtPrinter::VisitOMPMaskedDirective(OMPMaskedDirective *Node) {
981
12
  Indent() << "#pragma omp masked";
982
12
  PrintOMPExecutableDirective(Node);
983
12
}
984
985
//===----------------------------------------------------------------------===//
986
//  Expr printing methods.
987
//===----------------------------------------------------------------------===//
988
989
8
void StmtPrinter::VisitSourceLocExpr(SourceLocExpr *Node) {
990
8
  OS << Node->getBuiltinStr() << "()";
991
8
}
992
993
4.36k
void StmtPrinter::VisitConstantExpr(ConstantExpr *Node) {
994
4.36k
  PrintExpr(Node->getSubExpr());
995
4.36k
}
996
997
63.2k
void StmtPrinter::VisitDeclRefExpr(DeclRefExpr *Node) {
998
63.2k
  if (const auto *OCED = dyn_cast<OMPCapturedExprDecl>(Node->getDecl())) {
999
3.16k
    OCED->getInit()->IgnoreImpCasts()->printPretty(OS, nullptr, Policy);
1000
3.16k
    return;
1001
3.16k
  }
1002
60.1k
  if (const auto *TPOD = dyn_cast<TemplateParamObjectDecl>(Node->getDecl())) {
1003
4
    TPOD->printAsExpr(OS);
1004
4
    return;
1005
4
  }
1006
60.1k
  if (NestedNameSpecifier *Qualifier = Node->getQualifier())
1007
225
    Qualifier->print(OS, Policy);
1008
60.1k
  if (Node->hasTemplateKeyword())
1009
2
    OS << "template ";
1010
60.1k
  OS << Node->getNameInfo();
1011
60.1k
  if (Node->hasExplicitTemplateArgs()) {
1012
713
    const TemplateParameterList *TPL = nullptr;
1013
713
    if (!Node->hadMultipleCandidates())
1014
699
      if (auto *TD = dyn_cast<TemplateDecl>(Node->getDecl()))
1015
0
        TPL = TD->getTemplateParameters();
1016
713
    printTemplateArgumentList(OS, Node->template_arguments(), Policy, TPL);
1017
713
  }
1018
60.1k
}
1019
1020
void StmtPrinter::VisitDependentScopeDeclRefExpr(
1021
175
                                           DependentScopeDeclRefExpr *Node) {
1022
175
  if (NestedNameSpecifier *Qualifier = Node->getQualifier())
1023
175
    Qualifier->print(OS, Policy);
1024
175
  if (Node->hasTemplateKeyword())
1025
8
    OS << "template ";
1026
175
  OS << Node->getNameInfo();
1027
175
  if (Node->hasExplicitTemplateArgs())
1028
6
    printTemplateArgumentList(OS, Node->template_arguments(), Policy);
1029
175
}
1030
1031
43
void StmtPrinter::VisitUnresolvedLookupExpr(UnresolvedLookupExpr *Node) {
1032
43
  if (Node->getQualifier())
1033
10
    Node->getQualifier()->print(OS, Policy);
1034
43
  if (Node->hasTemplateKeyword())
1035
5
    OS << "template ";
1036
43
  OS << Node->getNameInfo();
1037
43
  if (Node->hasExplicitTemplateArgs())
1038
24
    printTemplateArgumentList(OS, Node->template_arguments(), Policy);
1039
43
}
1040
1041
1
static bool isImplicitSelf(const Expr *E) {
1042
1
  if (const auto *DRE = dyn_cast<DeclRefExpr>(E)) {
1043
1
    if (const auto *PD = dyn_cast<ImplicitParamDecl>(DRE->getDecl())) {
1044
1
      if (PD->getParameterKind() == ImplicitParamDecl::ObjCSelf &&
1045
1
          DRE->getBeginLoc().isInvalid())
1046
1
        return true;
1047
1
    }
1048
1
  }
1049
0
  return false;
1050
1
}
1051
1052
28
void StmtPrinter::VisitObjCIvarRefExpr(ObjCIvarRefExpr *Node) {
1053
28
  if (Node->getBase()) {
1054
28
    if (!Policy.SuppressImplicitBase ||
1055
28
        
!isImplicitSelf(Node->getBase()->IgnoreImpCasts())1
) {
1056
27
      PrintExpr(Node->getBase());
1057
27
      OS << (Node->isArrow() ? 
"->"25
:
"."2
);
1058
27
    }
1059
28
  }
1060
28
  OS << *Node->getDecl();
1061
28
}
1062
1063
5
void StmtPrinter::VisitObjCPropertyRefExpr(ObjCPropertyRefExpr *Node) {
1064
5
  if (Node->isSuperReceiver())
1065
1
    OS << "super.";
1066
4
  else if (Node->isObjectReceiver() && 
Node->getBase()1
) {
1067
1
    PrintExpr(Node->getBase());
1068
1
    OS << ".";
1069
3
  } else if (Node->isClassReceiver() && Node->getClassReceiver()) {
1070
3
    OS << Node->getClassReceiver()->getName() << ".";
1071
3
  }
1072
1073
5
  if (Node->isImplicitProperty()) {
1074
4
    if (const auto *Getter = Node->getImplicitPropertyGetter())
1075
3
      Getter->getSelector().print(OS);
1076
1
    else
1077
1
      OS << SelectorTable::getPropertyNameFromSetterSelector(
1078
1
          Node->getImplicitPropertySetter()->getSelector());
1079
4
  } else
1080
1
    OS << Node->getExplicitProperty()->getName();
1081
5
}
1082
1083
4
void StmtPrinter::VisitObjCSubscriptRefExpr(ObjCSubscriptRefExpr *Node) {
1084
4
  PrintExpr(Node->getBaseExpr());
1085
4
  OS << "[";
1086
4
  PrintExpr(Node->getKeyExpr());
1087
4
  OS << "]";
1088
4
}
1089
1090
void StmtPrinter::VisitSYCLUniqueStableNameExpr(
1091
6
    SYCLUniqueStableNameExpr *Node) {
1092
6
  OS << "__builtin_sycl_unique_stable_name(";
1093
6
  Node->getTypeSourceInfo()->getType().print(OS, Policy);
1094
6
  OS << ")";
1095
6
}
1096
1097
15
void StmtPrinter::VisitPredefinedExpr(PredefinedExpr *Node) {
1098
15
  OS << PredefinedExpr::getIdentKindName(Node->getIdentKind());
1099
15
}
1100
1101
473
void StmtPrinter::VisitCharacterLiteral(CharacterLiteral *Node) {
1102
473
  CharacterLiteral::print(Node->getValue(), Node->getKind(), OS);
1103
473
}
1104
1105
/// Prints the given expression using the original source text. Returns true on
1106
/// success, false otherwise.
1107
static bool printExprAsWritten(raw_ostream &OS, Expr *E,
1108
14
                               const ASTContext *Context) {
1109
14
  if (!Context)
1110
2
    return false;
1111
12
  bool Invalid = false;
1112
12
  StringRef Source = Lexer::getSourceText(
1113
12
      CharSourceRange::getTokenRange(E->getSourceRange()),
1114
12
      Context->getSourceManager(), Context->getLangOpts(), &Invalid);
1115
12
  if (!Invalid) {
1116
11
    OS << Source;
1117
11
    return true;
1118
11
  }
1119
1
  return false;
1120
12
}
1121
1122
27.4k
void StmtPrinter::VisitIntegerLiteral(IntegerLiteral *Node) {
1123
27.4k
  if (Policy.ConstantsAsWritten && 
printExprAsWritten(OS, Node, Context)13
)
1124
10
    return;
1125
27.4k
  bool isSigned = Node->getType()->isSignedIntegerType();
1126
27.4k
  OS << toString(Node->getValue(), 10, isSigned);
1127
1128
  // Emit suffixes.  Integer literals are always a builtin integer type.
1129
27.4k
  switch (Node->getType()->castAs<BuiltinType>()->getKind()) {
1130
0
  default: llvm_unreachable("Unexpected type for integer literal!");
1131
2
  case BuiltinType::Char_S:
1132
2
  case BuiltinType::Char_U:    OS << "i8"; break;
1133
1
  case BuiltinType::UChar:     OS << "Ui8"; break;
1134
2
  case BuiltinType::Short:     OS << "i16"; break;
1135
1
  case BuiltinType::UShort:    OS << "Ui16"; break;
1136
27.2k
  case BuiltinType::Int:       break; // no suffix.
1137
145
  case BuiltinType::UInt:      OS << 'U'; break;
1138
27
  case BuiltinType::Long:      OS << 'L'; break;
1139
29
  case BuiltinType::ULong:     OS << "UL"; break;
1140
8
  case BuiltinType::LongLong:  OS << "LL"; break;
1141
2
  case BuiltinType::ULongLong: OS << "ULL"; break;
1142
0
  case BuiltinType::Int128:
1143
0
    break; // no suffix.
1144
1
  case BuiltinType::UInt128:
1145
1
    break; // no suffix.
1146
27.4k
  }
1147
27.4k
}
1148
1149
14
void StmtPrinter::VisitFixedPointLiteral(FixedPointLiteral *Node) {
1150
14
  if (Policy.ConstantsAsWritten && 
printExprAsWritten(OS, Node, Context)0
)
1151
0
    return;
1152
14
  OS << Node->getValueAsString(/*Radix=*/10);
1153
1154
14
  switch (Node->getType()->castAs<BuiltinType>()->getKind()) {
1155
0
    default: llvm_unreachable("Unexpected type for fixed point literal!");
1156
0
    case BuiltinType::ShortFract:   OS << "hr"; break;
1157
0
    case BuiltinType::ShortAccum:   OS << "hk"; break;
1158
0
    case BuiltinType::UShortFract:  OS << "uhr"; break;
1159
0
    case BuiltinType::UShortAccum:  OS << "uhk"; break;
1160
8
    case BuiltinType::Fract:        OS << "r"; break;
1161
4
    case BuiltinType::Accum:        OS << "k"; break;
1162
0
    case BuiltinType::UFract:       OS << "ur"; break;
1163
0
    case BuiltinType::UAccum:       OS << "uk"; break;
1164
0
    case BuiltinType::LongFract:    OS << "lr"; break;
1165
2
    case BuiltinType::LongAccum:    OS << "lk"; break;
1166
0
    case BuiltinType::ULongFract:   OS << "ulr"; break;
1167
0
    case BuiltinType::ULongAccum:   OS << "ulk"; break;
1168
14
  }
1169
14
}
1170
1171
static void PrintFloatingLiteral(raw_ostream &OS, FloatingLiteral *Node,
1172
157
                                 bool PrintSuffix) {
1173
157
  SmallString<16> Str;
1174
157
  Node->getValue().toString(Str);
1175
157
  OS << Str;
1176
157
  if (Str.find_first_not_of("-0123456789") == StringRef::npos)
1177
112
    OS << '.'; // Trailing dot in order to separate from ints.
1178
1179
157
  if (!PrintSuffix)
1180
2
    return;
1181
1182
  // Emit suffixes.  Float literals are always a builtin float type.
1183
155
  switch (Node->getType()->castAs<BuiltinType>()->getKind()) {
1184
0
  default: llvm_unreachable("Unexpected type for float literal!");
1185
0
  case BuiltinType::Half:       break; // FIXME: suffix?
1186
122
  case BuiltinType::Double:     break; // no suffix.
1187
0
  case BuiltinType::Float16:    OS << "F16"; break;
1188
21
  case BuiltinType::Float:      OS << 'F'; break;
1189
12
  case BuiltinType::LongDouble: OS << 'L'; break;
1190
0
  case BuiltinType::Float128:   OS << 'Q'; break;
1191
155
  }
1192
155
}
1193
1194
156
void StmtPrinter::VisitFloatingLiteral(FloatingLiteral *Node) {
1195
156
  if (Policy.ConstantsAsWritten && 
printExprAsWritten(OS, Node, Context)1
)
1196
1
    return;
1197
155
  PrintFloatingLiteral(OS, Node, /*PrintSuffix=*/true);
1198
155
}
1199
1200
22
void StmtPrinter::VisitImaginaryLiteral(ImaginaryLiteral *Node) {
1201
22
  PrintExpr(Node->getSubExpr());
1202
22
  OS << "i";
1203
22
}
1204
1205
822
void StmtPrinter::VisitStringLiteral(StringLiteral *Str) {
1206
822
  Str->outputString(OS);
1207
822
}
1208
1209
1.92k
void StmtPrinter::VisitParenExpr(ParenExpr *Node) {
1210
1.92k
  OS << "(";
1211
1.92k
  PrintExpr(Node->getSubExpr());
1212
1.92k
  OS << ")";
1213
1.92k
}
1214
1215
24.6k
void StmtPrinter::VisitUnaryOperator(UnaryOperator *Node) {
1216
24.6k
  if (!Node->isPostfix()) {
1217
23.0k
    OS << UnaryOperator::getOpcodeStr(Node->getOpcode());
1218
1219
    // Print a space if this is an "identifier operator" like __real, or if
1220
    // it might be concatenated incorrectly like '+'.
1221
23.0k
    switch (Node->getOpcode()) {
1222
22.9k
    default: break;
1223
22.9k
    case UO_Real:
1224
6
    case UO_Imag:
1225
8
    case UO_Extension:
1226
8
      OS << ' ';
1227
8
      break;
1228
11
    case UO_Plus:
1229
128
    case UO_Minus:
1230
128
      if (isa<UnaryOperator>(Node->getSubExpr()))
1231
0
        OS << ' ';
1232
128
      break;
1233
23.0k
    }
1234
23.0k
  }
1235
24.6k
  PrintExpr(Node->getSubExpr());
1236
1237
24.6k
  if (Node->isPostfix())
1238
1.59k
    OS << UnaryOperator::getOpcodeStr(Node->getOpcode());
1239
24.6k
}
1240
1241
2
void StmtPrinter::VisitOffsetOfExpr(OffsetOfExpr *Node) {
1242
2
  OS << "__builtin_offsetof(";
1243
2
  Node->getTypeSourceInfo()->getType().print(OS, Policy);
1244
2
  OS << ", ";
1245
2
  bool PrintedSomething = false;
1246
4
  for (unsigned i = 0, n = Node->getNumComponents(); i < n; 
++i2
) {
1247
2
    OffsetOfNode ON = Node->getComponent(i);
1248
2
    if (ON.getKind() == OffsetOfNode::Array) {
1249
      // Array node
1250
0
      OS << "[";
1251
0
      PrintExpr(Node->getIndexExpr(ON.getArrayExprIndex()));
1252
0
      OS << "]";
1253
0
      PrintedSomething = true;
1254
0
      continue;
1255
0
    }
1256
1257
    // Skip implicit base indirections.
1258
2
    if (ON.getKind() == OffsetOfNode::Base)
1259
0
      continue;
1260
1261
    // Field or identifier node.
1262
2
    IdentifierInfo *Id = ON.getFieldName();
1263
2
    if (!Id)
1264
0
      continue;
1265
1266
2
    if (PrintedSomething)
1267
0
      OS << ".";
1268
2
    else
1269
2
      PrintedSomething = true;
1270
2
    OS << Id->getName();
1271
2
  }
1272
2
  OS << ")";
1273
2
}
1274
1275
void StmtPrinter::VisitUnaryExprOrTypeTraitExpr(
1276
547
    UnaryExprOrTypeTraitExpr *Node) {
1277
547
  const char *Spelling = getTraitSpelling(Node->getKind());
1278
547
  if (Node->getKind() == UETT_AlignOf) {
1279
15
    if (Policy.Alignof)
1280
15
      Spelling = "alignof";
1281
0
    else if (Policy.UnderscoreAlignof)
1282
0
      Spelling = "_Alignof";
1283
0
    else
1284
0
      Spelling = "__alignof";
1285
15
  }
1286
1287
547
  OS << Spelling;
1288
1289
547
  if (Node->isArgumentType()) {
1290
399
    OS << '(';
1291
399
    Node->getArgumentType().print(OS, Policy);
1292
399
    OS << ')';
1293
399
  } else {
1294
148
    OS << " ";
1295
148
    PrintExpr(Node->getArgumentExpr());
1296
148
  }
1297
547
}
1298
1299
4
void StmtPrinter::VisitGenericSelectionExpr(GenericSelectionExpr *Node) {
1300
4
  OS << "_Generic(";
1301
4
  PrintExpr(Node->getControllingExpr());
1302
8
  for (const GenericSelectionExpr::Association Assoc : Node->associations()) {
1303
8
    OS << ", ";
1304
8
    QualType T = Assoc.getType();
1305
8
    if (T.isNull())
1306
0
      OS << "default";
1307
8
    else
1308
8
      T.print(OS, Policy);
1309
8
    OS << ": ";
1310
8
    PrintExpr(Assoc.getAssociationExpr());
1311
8
  }
1312
4
  OS << ")";
1313
4
}
1314
1315
1.52k
void StmtPrinter::VisitArraySubscriptExpr(ArraySubscriptExpr *Node) {
1316
1.52k
  PrintExpr(Node->getLHS());
1317
1.52k
  OS << "[";
1318
1.52k
  PrintExpr(Node->getRHS());
1319
1.52k
  OS << "]";
1320
1.52k
}
1321
1322
0
void StmtPrinter::VisitMatrixSubscriptExpr(MatrixSubscriptExpr *Node) {
1323
0
  PrintExpr(Node->getBase());
1324
0
  OS << "[";
1325
0
  PrintExpr(Node->getRowIdx());
1326
0
  OS << "]";
1327
0
  OS << "[";
1328
0
  PrintExpr(Node->getColumnIdx());
1329
0
  OS << "]";
1330
0
}
1331
1332
3.80k
void StmtPrinter::VisitOMPArraySectionExpr(OMPArraySectionExpr *Node) {
1333
3.80k
  PrintExpr(Node->getBase());
1334
3.80k
  OS << "[";
1335
3.80k
  if (Node->getLowerBound())
1336
1.91k
    PrintExpr(Node->getLowerBound());
1337
3.80k
  if (Node->getColonLocFirst().isValid()) {
1338
3.75k
    OS << ":";
1339
3.75k
    if (Node->getLength())
1340
2.77k
      PrintExpr(Node->getLength());
1341
3.75k
  }
1342
3.80k
  if (Node->getColonLocSecond().isValid()) {
1343
200
    OS << ":";
1344
200
    if (Node->getStride())
1345
152
      PrintExpr(Node->getStride());
1346
200
  }
1347
3.80k
  OS << "]";
1348
3.80k
}
1349
1350
96
void StmtPrinter::VisitOMPArrayShapingExpr(OMPArrayShapingExpr *Node) {
1351
96
  OS << "(";
1352
208
  for (Expr *E : Node->getDimensions()) {
1353
208
    OS << "[";
1354
208
    PrintExpr(E);
1355
208
    OS << "]";
1356
208
  }
1357
96
  OS << ")";
1358
96
  PrintExpr(Node->getBase());
1359
96
}
1360
1361
28
void StmtPrinter::VisitOMPIteratorExpr(OMPIteratorExpr *Node) {
1362
28
  OS << "iterator(";
1363
76
  for (unsigned I = 0, E = Node->numOfIterators(); I < E; 
++I48
) {
1364
48
    auto *VD = cast<ValueDecl>(Node->getIteratorDecl(I));
1365
48
    VD->getType().print(OS, Policy);
1366
48
    const OMPIteratorExpr::IteratorRange Range = Node->getIteratorRange(I);
1367
48
    OS << " " << VD->getName() << " = ";
1368
48
    PrintExpr(Range.Begin);
1369
48
    OS << ":";
1370
48
    PrintExpr(Range.End);
1371
48
    if (Range.Step) {
1372
20
      OS << ":";
1373
20
      PrintExpr(Range.Step);
1374
20
    }
1375
48
    if (I < E - 1)
1376
20
      OS << ", ";
1377
48
  }
1378
28
  OS << ")";
1379
28
}
1380
1381
5.03k
void StmtPrinter::PrintCallArgs(CallExpr *Call) {
1382
8.16k
  for (unsigned i = 0, e = Call->getNumArgs(); i != e; 
++i3.13k
) {
1383
3.13k
    if (isa<CXXDefaultArgExpr>(Call->getArg(i))) {
1384
      // Don't print any defaulted arguments
1385
2
      break;
1386
2
    }
1387
1388
3.13k
    if (i) 
OS << ", "1.30k
;
1389
3.13k
    PrintExpr(Call->getArg(i));
1390
3.13k
  }
1391
5.03k
}
1392
1393
5.03k
void StmtPrinter::VisitCallExpr(CallExpr *Call) {
1394
5.03k
  PrintExpr(Call->getCallee());
1395
5.03k
  OS << "(";
1396
5.03k
  PrintCallArgs(Call);
1397
5.03k
  OS << ")";
1398
5.03k
}
1399
1400
1
static bool isImplicitThis(const Expr *E) {
1401
1
  if (const auto *TE = dyn_cast<CXXThisExpr>(E))
1402
1
    return TE->isImplicit();
1403
0
  return false;
1404
1
}
1405
1406
6.76k
void StmtPrinter::VisitMemberExpr(MemberExpr *Node) {
1407
6.76k
  if (!Policy.SuppressImplicitBase || 
!isImplicitThis(Node->getBase())1
) {
1408
6.76k
    PrintExpr(Node->getBase());
1409
1410
6.76k
    auto *ParentMember = dyn_cast<MemberExpr>(Node->getBase());
1411
6.76k
    FieldDecl *ParentDecl =
1412
6.76k
        ParentMember ? 
dyn_cast<FieldDecl>(ParentMember->getMemberDecl())711
1413
6.76k
                     : 
nullptr6.05k
;
1414
1415
6.76k
    if (!ParentDecl || 
!ParentDecl->isAnonymousStructOrUnion()711
)
1416
6.76k
      OS << (Node->isArrow() ? 
"->"4.32k
:
"."2.43k
);
1417
6.76k
  }
1418
1419
6.76k
  if (auto *FD = dyn_cast<FieldDecl>(Node->getMemberDecl()))
1420
6.38k
    if (FD->isAnonymousStructOrUnion())
1421
4
      return;
1422
1423
6.76k
  if (NestedNameSpecifier *Qualifier = Node->getQualifier())
1424
718
    Qualifier->print(OS, Policy);
1425
6.76k
  if (Node->hasTemplateKeyword())
1426
7
    OS << "template ";
1427
6.76k
  OS << Node->getMemberNameInfo();
1428
6.76k
  const TemplateParameterList *TPL = nullptr;
1429
6.76k
  if (auto *FD = dyn_cast<FunctionDecl>(Node->getMemberDecl())) {
1430
358
    if (!Node->hadMultipleCandidates())
1431
237
      if (auto *FTD = FD->getPrimaryTemplate())
1432
0
        TPL = FTD->getTemplateParameters();
1433
6.40k
  } else if (auto *VTSD =
1434
6.40k
                 dyn_cast<VarTemplateSpecializationDecl>(Node->getMemberDecl()))
1435
15
    TPL = VTSD->getSpecializedTemplate()->getTemplateParameters();
1436
6.76k
  if (Node->hasExplicitTemplateArgs())
1437
9
    printTemplateArgumentList(OS, Node->template_arguments(), Policy, TPL);
1438
6.76k
}
1439
1440
0
void StmtPrinter::VisitObjCIsaExpr(ObjCIsaExpr *Node) {
1441
0
  PrintExpr(Node->getBase());
1442
0
  OS << (Node->isArrow() ? "->isa" : ".isa");
1443
0
}
1444
1445
8
void StmtPrinter::VisitExtVectorElementExpr(ExtVectorElementExpr *Node) {
1446
8
  PrintExpr(Node->getBase());
1447
8
  OS << ".";
1448
8
  OS << Node->getAccessor().getName();
1449
8
}
1450
1451
2.21k
void StmtPrinter::VisitCStyleCastExpr(CStyleCastExpr *Node) {
1452
2.21k
  OS << '(';
1453
2.21k
  Node->getTypeAsWritten().print(OS, Policy);
1454
2.21k
  OS << ')';
1455
2.21k
  PrintExpr(Node->getSubExpr());
1456
2.21k
}
1457
1458
23
void StmtPrinter::VisitCompoundLiteralExpr(CompoundLiteralExpr *Node) {
1459
23
  OS << '(';
1460
23
  Node->getType().print(OS, Policy);
1461
23
  OS << ')';
1462
23
  PrintExpr(Node->getInitializer());
1463
23
}
1464
1465
46.0k
void StmtPrinter::VisitImplicitCastExpr(ImplicitCastExpr *Node) {
1466
  // No need to print anything, simply forward to the subexpression.
1467
46.0k
  PrintExpr(Node->getSubExpr());
1468
46.0k
}
1469
1470
13.8k
void StmtPrinter::VisitBinaryOperator(BinaryOperator *Node) {
1471
13.8k
  PrintExpr(Node->getLHS());
1472
13.8k
  OS << " " << BinaryOperator::getOpcodeStr(Node->getOpcode()) << " ";
1473
13.8k
  PrintExpr(Node->getRHS());
1474
13.8k
}
1475
1476
533
void StmtPrinter::VisitCompoundAssignOperator(CompoundAssignOperator *Node) {
1477
533
  PrintExpr(Node->getLHS());
1478
533
  OS << " " << BinaryOperator::getOpcodeStr(Node->getOpcode()) << " ";
1479
533
  PrintExpr(Node->getRHS());
1480
533
}
1481
1482
143
void StmtPrinter::VisitConditionalOperator(ConditionalOperator *Node) {
1483
143
  PrintExpr(Node->getCond());
1484
143
  OS << " ? ";
1485
143
  PrintExpr(Node->getLHS());
1486
143
  OS << " : ";
1487
143
  PrintExpr(Node->getRHS());
1488
143
}
1489
1490
// GNU extensions.
1491
1492
void
1493
39
StmtPrinter::VisitBinaryConditionalOperator(BinaryConditionalOperator *Node) {
1494
39
  PrintExpr(Node->getCommon());
1495
39
  OS << " ?: ";
1496
39
  PrintExpr(Node->getFalseExpr());
1497
39
}
1498
1499
46
void StmtPrinter::VisitAddrLabelExpr(AddrLabelExpr *Node) {
1500
46
  OS << "&&" << Node->getLabel()->getName();
1501
46
}
1502
1503
6
void StmtPrinter::VisitStmtExpr(StmtExpr *E) {
1504
6
  OS << "(";
1505
6
  PrintRawCompoundStmt(E->getSubStmt());
1506
6
  OS << ")";
1507
6
}
1508
1509
4
void StmtPrinter::VisitChooseExpr(ChooseExpr *Node) {
1510
4
  OS << "__builtin_choose_expr(";
1511
4
  PrintExpr(Node->getCond());
1512
4
  OS << ", ";
1513
4
  PrintExpr(Node->getLHS());
1514
4
  OS << ", ";
1515
4
  PrintExpr(Node->getRHS());
1516
4
  OS << ")";
1517
4
}
1518
1519
4
void StmtPrinter::VisitGNUNullExpr(GNUNullExpr *) {
1520
4
  OS << "__null";
1521
4
}
1522
1523
0
void StmtPrinter::VisitShuffleVectorExpr(ShuffleVectorExpr *Node) {
1524
0
  OS << "__builtin_shufflevector(";
1525
0
  for (unsigned i = 0, e = Node->getNumSubExprs(); i != e; ++i) {
1526
0
    if (i) OS << ", ";
1527
0
    PrintExpr(Node->getExpr(i));
1528
0
  }
1529
0
  OS << ")";
1530
0
}
1531
1532
0
void StmtPrinter::VisitConvertVectorExpr(ConvertVectorExpr *Node) {
1533
0
  OS << "__builtin_convertvector(";
1534
0
  PrintExpr(Node->getSrcExpr());
1535
0
  OS << ", ";
1536
0
  Node->getType().print(OS, Policy);
1537
0
  OS << ")";
1538
0
}
1539
1540
900
void StmtPrinter::VisitInitListExpr(InitListExpr* Node) {
1541
900
  if (Node->getSyntacticForm()) {
1542
392
    Visit(Node->getSyntacticForm());
1543
392
    return;
1544
392
  }
1545
1546
508
  OS << "{";
1547
1.35k
  for (unsigned i = 0, e = Node->getNumInits(); i != e; 
++i848
) {
1548
848
    if (i) 
OS << ", "379
;
1549
848
    if (Node->getInit(i))
1550
848
      PrintExpr(Node->getInit(i));
1551
0
    else
1552
0
      OS << "{}";
1553
848
  }
1554
508
  OS << "}";
1555
508
}
1556
1557
0
void StmtPrinter::VisitArrayInitLoopExpr(ArrayInitLoopExpr *Node) {
1558
  // There's no way to express this expression in any of our supported
1559
  // languages, so just emit something terse and (hopefully) clear.
1560
0
  OS << "{";
1561
0
  PrintExpr(Node->getSubExpr());
1562
0
  OS << "}";
1563
0
}
1564
1565
0
void StmtPrinter::VisitArrayInitIndexExpr(ArrayInitIndexExpr *Node) {
1566
0
  OS << "*";
1567
0
}
1568
1569
9
void StmtPrinter::VisitParenListExpr(ParenListExpr* Node) {
1570
9
  OS << "(";
1571
19
  for (unsigned i = 0, e = Node->getNumExprs(); i != e; 
++i10
) {
1572
10
    if (i) 
OS << ", "1
;
1573
10
    PrintExpr(Node->getExpr(i));
1574
10
  }
1575
9
  OS << ")";
1576
9
}
1577
1578
38
void StmtPrinter::VisitDesignatedInitExpr(DesignatedInitExpr *Node) {
1579
38
  bool NeedsEquals = true;
1580
70
  for (const DesignatedInitExpr::Designator &D : Node->designators()) {
1581
70
    if (D.isFieldDesignator()) {
1582
42
      if (D.getDotLoc().isInvalid()) {
1583
3
        if (IdentifierInfo *II = D.getFieldName()) {
1584
1
          OS << II->getName() << ":";
1585
1
          NeedsEquals = false;
1586
1
        }
1587
39
      } else {
1588
39
        OS << "." << D.getFieldName()->getName();
1589
39
      }
1590
42
    } else {
1591
28
      OS << "[";
1592
28
      if (D.isArrayDesignator()) {
1593
28
        PrintExpr(Node->getArrayIndex(D));
1594
28
      } else {
1595
0
        PrintExpr(Node->getArrayRangeStart(D));
1596
0
        OS << " ... ";
1597
0
        PrintExpr(Node->getArrayRangeEnd(D));
1598
0
      }
1599
28
      OS << "]";
1600
28
    }
1601
70
  }
1602
1603
38
  if (NeedsEquals)
1604
37
    OS << " = ";
1605
1
  else
1606
1
    OS << " ";
1607
38
  PrintExpr(Node->getInit());
1608
38
}
1609
1610
void StmtPrinter::VisitDesignatedInitUpdateExpr(
1611
2
    DesignatedInitUpdateExpr *Node) {
1612
2
  OS << "{";
1613
2
  OS << "/*base*/";
1614
2
  PrintExpr(Node->getBase());
1615
2
  OS << ", ";
1616
1617
2
  OS << "/*updater*/";
1618
2
  PrintExpr(Node->getUpdater());
1619
2
  OS << "}";
1620
2
}
1621
1622
4
void StmtPrinter::VisitNoInitExpr(NoInitExpr *Node) {
1623
4
  OS << "/*no init*/";
1624
4
}
1625
1626
6
void StmtPrinter::VisitImplicitValueInitExpr(ImplicitValueInitExpr *Node) {
1627
6
  if (Node->getType()->getAsCXXRecordDecl()) {
1628
0
    OS << "/*implicit*/";
1629
0
    Node->getType().print(OS, Policy);
1630
0
    OS << "()";
1631
6
  } else {
1632
6
    OS << "/*implicit*/(";
1633
6
    Node->getType().print(OS, Policy);
1634
6
    OS << ')';
1635
6
    if (Node->getType()->isRecordType())
1636
0
      OS << "{}";
1637
6
    else
1638
6
      OS << 0;
1639
6
  }
1640
6
}
1641
1642
6
void StmtPrinter::VisitVAArgExpr(VAArgExpr *Node) {
1643
6
  OS << "__builtin_va_arg(";
1644
6
  PrintExpr(Node->getSubExpr());
1645
6
  OS << ", ";
1646
6
  Node->getType().print(OS, Policy);
1647
6
  OS << ")";
1648
6
}
1649
1650
33
void StmtPrinter::VisitPseudoObjectExpr(PseudoObjectExpr *Node) {
1651
33
  PrintExpr(Node->getSyntacticForm());
1652
33
}
1653
1654
6
void StmtPrinter::VisitAtomicExpr(AtomicExpr *Node) {
1655
6
  const char *Name = nullptr;
1656
6
  switch (Node->getOp()) {
1657
0
#define BUILTIN(ID, TYPE, ATTRS)
1658
0
#define ATOMIC_BUILTIN(ID, TYPE, ATTRS) \
1659
6
  case AtomicExpr::AO ## ID: \
1660
6
    Name = #ID "("; \
1661
6
    break;
1662
6
#include 
"clang/Basic/Builtins.def"0
1663
6
  }
1664
6
  OS << Name;
1665
1666
  // AtomicExpr stores its subexpressions in a permuted order.
1667
6
  PrintExpr(Node->getPtr());
1668
6
  if (Node->getOp() != AtomicExpr::AO__c11_atomic_load &&
1669
6
      
Node->getOp() != AtomicExpr::AO__atomic_load_n5
&&
1670
6
      
Node->getOp() != AtomicExpr::AO__opencl_atomic_load1
) {
1671
1
    OS << ", ";
1672
1
    PrintExpr(Node->getVal1());
1673
1
  }
1674
6
  if (Node->getOp() == AtomicExpr::AO__atomic_exchange ||
1675
6
      Node->isCmpXChg()) {
1676
0
    OS << ", ";
1677
0
    PrintExpr(Node->getVal2());
1678
0
  }
1679
6
  if (Node->getOp() == AtomicExpr::AO__atomic_compare_exchange ||
1680
6
      Node->getOp() == AtomicExpr::AO__atomic_compare_exchange_n) {
1681
0
    OS << ", ";
1682
0
    PrintExpr(Node->getWeak());
1683
0
  }
1684
6
  if (Node->getOp() != AtomicExpr::AO__c11_atomic_init &&
1685
6
      
Node->getOp() != AtomicExpr::AO__opencl_atomic_init5
) {
1686
5
    OS << ", ";
1687
5
    PrintExpr(Node->getOrder());
1688
5
  }
1689
6
  if (Node->isCmpXChg()) {
1690
0
    OS << ", ";
1691
0
    PrintExpr(Node->getOrderFail());
1692
0
  }
1693
6
  OS << ")";
1694
6
}
1695
1696
// C++
1697
142
void StmtPrinter::VisitCXXOperatorCallExpr(CXXOperatorCallExpr *Node) {
1698
142
  OverloadedOperatorKind Kind = Node->getOperator();
1699
142
  if (Kind == OO_PlusPlus || 
Kind == OO_MinusMinus141
) {
1700
1
    if (Node->getNumArgs() == 1) {
1701
0
      OS << getOperatorSpelling(Kind) << ' ';
1702
0
      PrintExpr(Node->getArg(0));
1703
1
    } else {
1704
1
      PrintExpr(Node->getArg(0));
1705
1
      OS << ' ' << getOperatorSpelling(Kind);
1706
1
    }
1707
141
  } else if (Kind == OO_Arrow) {
1708
3
    PrintExpr(Node->getArg(0));
1709
138
  } else if (Kind == OO_Call) {
1710
83
    PrintExpr(Node->getArg(0));
1711
83
    OS << '(';
1712
97
    for (unsigned ArgIdx = 1; ArgIdx < Node->getNumArgs(); 
++ArgIdx14
) {
1713
14
      if (ArgIdx > 1)
1714
3
        OS << ", ";
1715
14
      if (!isa<CXXDefaultArgExpr>(Node->getArg(ArgIdx)))
1716
13
        PrintExpr(Node->getArg(ArgIdx));
1717
14
    }
1718
83
    OS << ')';
1719
83
  } else 
if (55
Kind == OO_Subscript55
) {
1720
0
    PrintExpr(Node->getArg(0));
1721
0
    OS << '[';
1722
0
    PrintExpr(Node->getArg(1));
1723
0
    OS << ']';
1724
55
  } else if (Node->getNumArgs() == 1) {
1725
1
    OS << getOperatorSpelling(Kind) << ' ';
1726
1
    PrintExpr(Node->getArg(0));
1727
54
  } else if (Node->getNumArgs() == 2) {
1728
54
    PrintExpr(Node->getArg(0));
1729
54
    OS << ' ' << getOperatorSpelling(Kind) << ' ';
1730
54
    PrintExpr(Node->getArg(1));
1731
54
  } else {
1732
0
    llvm_unreachable("unknown overloaded operator");
1733
0
  }
1734
142
}
1735
1736
425
void StmtPrinter::VisitCXXMemberCallExpr(CXXMemberCallExpr *Node) {
1737
  // If we have a conversion operator call only print the argument.
1738
425
  CXXMethodDecl *MD = Node->getMethodDecl();
1739
425
  if (MD && isa<CXXConversionDecl>(MD)) {
1740
289
    PrintExpr(Node->getImplicitObjectArgument());
1741
289
    return;
1742
289
  }
1743
136
  VisitCallExpr(cast<CallExpr>(Node));
1744
136
}
1745
1746
0
void StmtPrinter::VisitCUDAKernelCallExpr(CUDAKernelCallExpr *Node) {
1747
0
  PrintExpr(Node->getCallee());
1748
0
  OS << "<<<";
1749
0
  PrintCallArgs(Node->getConfig());
1750
0
  OS << ">>>(";
1751
0
  PrintCallArgs(Node);
1752
0
  OS << ")";
1753
0
}
1754
1755
void StmtPrinter::VisitCXXRewrittenBinaryOperator(
1756
21
    CXXRewrittenBinaryOperator *Node) {
1757
21
  CXXRewrittenBinaryOperator::DecomposedForm Decomposed =
1758
21
      Node->getDecomposedForm();
1759
21
  PrintExpr(const_cast<Expr*>(Decomposed.LHS));
1760
21
  OS << ' ' << BinaryOperator::getOpcodeStr(Decomposed.Opcode) << ' ';
1761
21
  PrintExpr(const_cast<Expr*>(Decomposed.RHS));
1762
21
}
1763
1764
31
void StmtPrinter::VisitCXXNamedCastExpr(CXXNamedCastExpr *Node) {
1765
31
  OS << Node->getCastName() << '<';
1766
31
  Node->getTypeAsWritten().print(OS, Policy);
1767
31
  OS << ">(";
1768
31
  PrintExpr(Node->getSubExpr());
1769
31
  OS << ")";
1770
31
}
1771
1772
19
void StmtPrinter::VisitCXXStaticCastExpr(CXXStaticCastExpr *Node) {
1773
19
  VisitCXXNamedCastExpr(Node);
1774
19
}
1775
1776
4
void StmtPrinter::VisitCXXDynamicCastExpr(CXXDynamicCastExpr *Node) {
1777
4
  VisitCXXNamedCastExpr(Node);
1778
4
}
1779
1780
4
void StmtPrinter::VisitCXXReinterpretCastExpr(CXXReinterpretCastExpr *Node) {
1781
4
  VisitCXXNamedCastExpr(Node);
1782
4
}
1783
1784
4
void StmtPrinter::VisitCXXConstCastExpr(CXXConstCastExpr *Node) {
1785
4
  VisitCXXNamedCastExpr(Node);
1786
4
}
1787
1788
0
void StmtPrinter::VisitBuiltinBitCastExpr(BuiltinBitCastExpr *Node) {
1789
0
  OS << "__builtin_bit_cast(";
1790
0
  Node->getTypeInfoAsWritten()->getType().print(OS, Policy);
1791
0
  OS << ", ";
1792
0
  PrintExpr(Node->getSubExpr());
1793
0
  OS << ")";
1794
0
}
1795
1796
0
void StmtPrinter::VisitCXXAddrspaceCastExpr(CXXAddrspaceCastExpr *Node) {
1797
0
  VisitCXXNamedCastExpr(Node);
1798
0
}
1799
1800
28
void StmtPrinter::VisitCXXTypeidExpr(CXXTypeidExpr *Node) {
1801
28
  OS << "typeid(";
1802
28
  if (Node->isTypeOperand()) {
1803
14
    Node->getTypeOperandSourceInfo()->getType().print(OS, Policy);
1804
14
  } else {
1805
14
    PrintExpr(Node->getExprOperand());
1806
14
  }
1807
28
  OS << ")";
1808
28
}
1809
1810
0
void StmtPrinter::VisitCXXUuidofExpr(CXXUuidofExpr *Node) {
1811
0
  OS << "__uuidof(";
1812
0
  if (Node->isTypeOperand()) {
1813
0
    Node->getTypeOperandSourceInfo()->getType().print(OS, Policy);
1814
0
  } else {
1815
0
    PrintExpr(Node->getExprOperand());
1816
0
  }
1817
0
  OS << ")";
1818
0
}
1819
1820
22
void StmtPrinter::VisitMSPropertyRefExpr(MSPropertyRefExpr *Node) {
1821
22
  PrintExpr(Node->getBaseExpr());
1822
22
  if (Node->isArrow())
1823
22
    OS << "->";
1824
0
  else
1825
0
    OS << ".";
1826
22
  if (NestedNameSpecifier *Qualifier =
1827
22
      Node->getQualifierLoc().getNestedNameSpecifier())
1828
0
    Qualifier->print(OS, Policy);
1829
22
  OS << Node->getPropertyDecl()->getDeclName();
1830
22
}
1831
1832
40
void StmtPrinter::VisitMSPropertySubscriptExpr(MSPropertySubscriptExpr *Node) {
1833
40
  PrintExpr(Node->getBase());
1834
40
  OS << "[";
1835
40
  PrintExpr(Node->getIdx());
1836
40
  OS << "]";
1837
40
}
1838
1839
14
void StmtPrinter::VisitUserDefinedLiteral(UserDefinedLiteral *Node) {
1840
14
  switch (Node->getLiteralOperatorKind()) {
1841
2
  case UserDefinedLiteral::LOK_Raw:
1842
2
    OS << cast<StringLiteral>(Node->getArg(0)->IgnoreImpCasts())->getString();
1843
2
    break;
1844
3
  case UserDefinedLiteral::LOK_Template: {
1845
3
    const auto *DRE = cast<DeclRefExpr>(Node->getCallee()->IgnoreImpCasts());
1846
3
    const TemplateArgumentList *Args =
1847
3
      cast<FunctionDecl>(DRE->getDecl())->getTemplateSpecializationArgs();
1848
3
    assert(Args);
1849
1850
3
    if (Args->size() != 1) {
1851
1
      const TemplateParameterList *TPL = nullptr;
1852
1
      if (!DRE->hadMultipleCandidates())
1853
1
        if (const auto *TD = dyn_cast<TemplateDecl>(DRE->getDecl()))
1854
0
          TPL = TD->getTemplateParameters();
1855
1
      OS << "operator\"\"" << Node->getUDSuffix()->getName();
1856
1
      printTemplateArgumentList(OS, Args->asArray(), Policy, TPL);
1857
1
      OS << "()";
1858
1
      return;
1859
1
    }
1860
1861
2
    const TemplateArgument &Pack = Args->get(0);
1862
16
    for (const auto &P : Pack.pack_elements()) {
1863
16
      char C = (char)P.getAsIntegral().getZExtValue();
1864
16
      OS << C;
1865
16
    }
1866
2
    break;
1867
3
  }
1868
2
  case UserDefinedLiteral::LOK_Integer: {
1869
    // Print integer literal without suffix.
1870
2
    const auto *Int = cast<IntegerLiteral>(Node->getCookedLiteral());
1871
2
    OS << toString(Int->getValue(), 10, /*isSigned*/false);
1872
2
    break;
1873
3
  }
1874
2
  case UserDefinedLiteral::LOK_Floating: {
1875
    // Print floating literal without suffix.
1876
2
    auto *Float = cast<FloatingLiteral>(Node->getCookedLiteral());
1877
2
    PrintFloatingLiteral(OS, Float, /*PrintSuffix=*/false);
1878
2
    break;
1879
3
  }
1880
4
  case UserDefinedLiteral::LOK_String:
1881
5
  case UserDefinedLiteral::LOK_Character:
1882
5
    PrintExpr(Node->getCookedLiteral());
1883
5
    break;
1884
14
  }
1885
13
  OS << Node->getUDSuffix()->getName();
1886
13
}
1887
1888
788
void StmtPrinter::VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *Node) {
1889
788
  OS << (Node->getValue() ? 
"true"551
:
"false"237
);
1890
788
}
1891
1892
107
void StmtPrinter::VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *Node) {
1893
107
  OS << "nullptr";
1894
107
}
1895
1896
4.87k
void StmtPrinter::VisitCXXThisExpr(CXXThisExpr *Node) {
1897
4.87k
  OS << "this";
1898
4.87k
}
1899
1900
2
void StmtPrinter::VisitCXXThrowExpr(CXXThrowExpr *Node) {
1901
2
  if (!Node->getSubExpr())
1902
2
    OS << "throw";
1903
0
  else {
1904
0
    OS << "throw ";
1905
0
    PrintExpr(Node->getSubExpr());
1906
0
  }
1907
2
}
1908
1909
8
void StmtPrinter::VisitCXXDefaultArgExpr(CXXDefaultArgExpr *Node) {
1910
  // Nothing to print: we picked up the default argument.
1911
8
}
1912
1913
1
void StmtPrinter::VisitCXXDefaultInitExpr(CXXDefaultInitExpr *Node) {
1914
  // Nothing to print: we picked up the default initializer.
1915
1
}
1916
1917
287
void StmtPrinter::VisitCXXFunctionalCastExpr(CXXFunctionalCastExpr *Node) {
1918
287
  Node->getType().print(OS, Policy);
1919
  // If there are no parens, this is list-initialization, and the braces are
1920
  // part of the syntax of the inner construct.
1921
287
  if (Node->getLParenLoc().isValid())
1922
188
    OS << "(";
1923
287
  PrintExpr(Node->getSubExpr());
1924
287
  if (Node->getLParenLoc().isValid())
1925
188
    OS << ")";
1926
287
}
1927
1928
876
void StmtPrinter::VisitCXXBindTemporaryExpr(CXXBindTemporaryExpr *Node) {
1929
876
  PrintExpr(Node->getSubExpr());
1930
876
}
1931
1932
756
void StmtPrinter::VisitCXXTemporaryObjectExpr(CXXTemporaryObjectExpr *Node) {
1933
756
  Node->getType().print(OS, Policy);
1934
756
  if (Node->isStdInitListInitialization())
1935
0
    /* Nothing to do; braces are part of creating the std::initializer_list. */;
1936
756
  else if (Node->isListInitialization())
1937
53
    OS << "{";
1938
703
  else
1939
703
    OS << "(";
1940
756
  for (CXXTemporaryObjectExpr::arg_iterator Arg = Node->arg_begin(),
1941
756
                                         ArgEnd = Node->arg_end();
1942
769
       Arg != ArgEnd; 
++Arg13
) {
1943
14
    if ((*Arg)->isDefaultArgument())
1944
1
      break;
1945
13
    if (Arg != Node->arg_begin())
1946
7
      OS << ", ";
1947
13
    PrintExpr(*Arg);
1948
13
  }
1949
756
  if (Node->isStdInitListInitialization())
1950
0
    /* See above. */;
1951
756
  else if (Node->isListInitialization())
1952
53
    OS << "}";
1953
703
  else
1954
703
    OS << ")";
1955
756
}
1956
1957
140
void StmtPrinter::VisitLambdaExpr(LambdaExpr *Node) {
1958
140
  OS << '[';
1959
140
  bool NeedComma = false;
1960
140
  switch (Node->getCaptureDefault()) {
1961
78
  case LCD_None:
1962
78
    break;
1963
1964
10
  case LCD_ByCopy:
1965
10
    OS << '=';
1966
10
    NeedComma = true;
1967
10
    break;
1968
1969
52
  case LCD_ByRef:
1970
52
    OS << '&';
1971
52
    NeedComma = true;
1972
52
    break;
1973
140
  }
1974
140
  for (LambdaExpr::capture_iterator C = Node->explicit_capture_begin(),
1975
140
                                 CEnd = Node->explicit_capture_end();
1976
210
       C != CEnd;
1977
140
       
++C70
) {
1978
70
    if (C->capturesVLAType())
1979
1
      continue;
1980
1981
69
    if (NeedComma)
1982
15
      OS << ", ";
1983
69
    NeedComma = true;
1984
1985
69
    switch (C->getCaptureKind()) {
1986
5
    case LCK_This:
1987
5
      OS << "this";
1988
5
      break;
1989
1990
0
    case LCK_StarThis:
1991
0
      OS << "*this";
1992
0
      break;
1993
1994
25
    case LCK_ByRef:
1995
25
      if (Node->getCaptureDefault() != LCD_ByRef || 
Node->isInitCapture(C)0
)
1996
25
        OS << '&';
1997
25
      OS << C->getCapturedVar()->getName();
1998
25
      break;
1999
2000
39
    case LCK_ByCopy:
2001
39
      OS << C->getCapturedVar()->getName();
2002
39
      break;
2003
2004
0
    case LCK_VLAType:
2005
0
      llvm_unreachable("VLA type in explicit captures.");
2006
69
    }
2007
2008
69
    if (C->isPackExpansion())
2009
4
      OS << "...";
2010
2011
69
    if (Node->isInitCapture(C)) {
2012
17
      VarDecl *D = C->getCapturedVar();
2013
2014
17
      llvm::StringRef Pre;
2015
17
      llvm::StringRef Post;
2016
17
      if (D->getInitStyle() == VarDecl::CallInit &&
2017
17
          
!isa<ParenListExpr>(D->getInit())8
) {
2018
5
        Pre = "(";
2019
5
        Post = ")";
2020
12
      } else if (D->getInitStyle() == VarDecl::CInit) {
2021
7
        Pre = " = ";
2022
7
      }
2023
2024
17
      OS << Pre;
2025
17
      PrintExpr(D->getInit());
2026
17
      OS << Post;
2027
17
    }
2028
69
  }
2029
140
  OS << ']';
2030
2031
140
  if (!Node->getExplicitTemplateParameters().empty()) {
2032
1
    Node->getTemplateParameterList()->print(
2033
1
        OS, Node->getLambdaClass()->getASTContext(),
2034
1
        /*OmitTemplateKW*/true);
2035
1
  }
2036
2037
140
  if (Node->hasExplicitParameters()) {
2038
93
    OS << '(';
2039
93
    CXXMethodDecl *Method = Node->getCallOperator();
2040
93
    NeedComma = false;
2041
93
    for (const auto *P : Method->parameters()) {
2042
33
      if (NeedComma) {
2043
14
        OS << ", ";
2044
19
      } else {
2045
19
        NeedComma = true;
2046
19
      }
2047
33
      std::string ParamStr = P->getNameAsString();
2048
33
      P->getOriginalType().print(OS, Policy, ParamStr);
2049
33
    }
2050
93
    if (Method->isVariadic()) {
2051
0
      if (NeedComma)
2052
0
        OS << ", ";
2053
0
      OS << "...";
2054
0
    }
2055
93
    OS << ')';
2056
2057
93
    if (Node->isMutable())
2058
11
      OS << " mutable";
2059
2060
93
    auto *Proto = Method->getType()->castAs<FunctionProtoType>();
2061
93
    Proto->printExceptionSpecification(OS, Policy);
2062
2063
    // FIXME: Attributes
2064
2065
    // Print the trailing return type if it was specified in the source.
2066
93
    if (Node->hasExplicitResultType()) {
2067
2
      OS << " -> ";
2068
2
      Proto->getReturnType().print(OS, Policy);
2069
2
    }
2070
93
  }
2071
2072
  // Print the body.
2073
140
  OS << ' ';
2074
140
  if (Policy.TerseOutput)
2075
1
    OS << "{}";
2076
139
  else
2077
139
    PrintRawCompoundStmt(Node->getCompoundStmtBody());
2078
140
}
2079
2080
266
void StmtPrinter::VisitCXXScalarValueInitExpr(CXXScalarValueInitExpr *Node) {
2081
266
  if (TypeSourceInfo *TSInfo = Node->getTypeSourceInfo())
2082
266
    TSInfo->getType().print(OS, Policy);
2083
0
  else
2084
0
    Node->getType().print(OS, Policy);
2085
266
  OS << "()";
2086
266
}
2087
2088
109
void StmtPrinter::VisitCXXNewExpr(CXXNewExpr *E) {
2089
109
  if (E->isGlobalNew())
2090
0
    OS << "::";
2091
109
  OS << "new ";
2092
109
  unsigned NumPlace = E->getNumPlacementArgs();
2093
109
  if (NumPlace > 0 && 
!isa<CXXDefaultArgExpr>(E->getPlacementArg(0))16
) {
2094
15
    OS << "(";
2095
15
    PrintExpr(E->getPlacementArg(0));
2096
15
    for (unsigned i = 1; i < NumPlace; 
++i0
) {
2097
1
      if (isa<CXXDefaultArgExpr>(E->getPlacementArg(i)))
2098
1
        break;
2099
0
      OS << ", ";
2100
0
      PrintExpr(E->getPlacementArg(i));
2101
0
    }
2102
15
    OS << ") ";
2103
15
  }
2104
109
  if (E->isParenTypeId())
2105
0
    OS << "(";
2106
109
  std::string TypeS;
2107
109
  if (Optional<Expr *> Size = E->getArraySize()) {
2108
11
    llvm::raw_string_ostream s(TypeS);
2109
11
    s << '[';
2110
11
    if (*Size)
2111
11
      (*Size)->printPretty(s, Helper, Policy);
2112
11
    s << ']';
2113
11
  }
2114
109
  E->getAllocatedType().print(OS, Policy, TypeS);
2115
109
  if (E->isParenTypeId())
2116
0
    OS << ")";
2117
2118
109
  CXXNewExpr::InitializationStyle InitStyle = E->getInitializationStyle();
2119
109
  if (InitStyle) {
2120
60
    if (InitStyle == CXXNewExpr::CallInit)
2121
60
      OS << "(";
2122
60
    PrintExpr(E->getInitializer());
2123
60
    if (InitStyle == CXXNewExpr::CallInit)
2124
60
      OS << ")";
2125
60
  }
2126
109
}
2127
2128
4
void StmtPrinter::VisitCXXDeleteExpr(CXXDeleteExpr *E) {
2129
4
  if (E->isGlobalDelete())
2130
0
    OS << "::";
2131
4
  OS << "delete ";
2132
4
  if (E->isArrayForm())
2133
2
    OS << "[] ";
2134
4
  PrintExpr(E->getArgument());
2135
4
}
2136
2137
5
void StmtPrinter::VisitCXXPseudoDestructorExpr(CXXPseudoDestructorExpr *E) {
2138
5
  PrintExpr(E->getBase());
2139
5
  if (E->isArrow())
2140
4
    OS << "->";
2141
1
  else
2142
1
    OS << '.';
2143
5
  if (E->getQualifier())
2144
0
    E->getQualifier()->print(OS, Policy);
2145
5
  OS << "~";
2146
2147
5
  if (IdentifierInfo *II = E->getDestroyedTypeIdentifier())
2148
0
    OS << II->getName();
2149
5
  else
2150
5
    E->getDestroyedType().print(OS, Policy);
2151
5
}
2152
2153
1.34k
void StmtPrinter::VisitCXXConstructExpr(CXXConstructExpr *E) {
2154
1.34k
  if (E->isListInitialization() && 
!E->isStdInitListInitialization()47
)
2155
47
    OS << "{";
2156
2157
2.25k
  for (unsigned i = 0, e = E->getNumArgs(); i != e; 
++i906
) {
2158
914
    if (isa<CXXDefaultArgExpr>(E->getArg(i))) {
2159
      // Don't print any defaulted arguments
2160
8
      break;
2161
8
    }
2162
2163
906
    if (i) 
OS << ", "7
;
2164
906
    PrintExpr(E->getArg(i));
2165
906
  }
2166
2167
1.34k
  if (E->isListInitialization() && 
!E->isStdInitListInitialization()47
)
2168
47
    OS << "}";
2169
1.34k
}
2170
2171
0
void StmtPrinter::VisitCXXInheritedCtorInitExpr(CXXInheritedCtorInitExpr *E) {
2172
  // Parens are printed by the surrounding context.
2173
0
  OS << "<forwarded>";
2174
0
}
2175
2176
0
void StmtPrinter::VisitCXXStdInitializerListExpr(CXXStdInitializerListExpr *E) {
2177
0
  PrintExpr(E->getSubExpr());
2178
0
}
2179
2180
380
void StmtPrinter::VisitExprWithCleanups(ExprWithCleanups *E) {
2181
  // Just forward to the subexpression.
2182
380
  PrintExpr(E->getSubExpr());
2183
380
}
2184
2185
void
2186
StmtPrinter::VisitCXXUnresolvedConstructExpr(
2187
245
                                           CXXUnresolvedConstructExpr *Node) {
2188
245
  Node->getTypeAsWritten().print(OS, Policy);
2189
245
  OS << "(";
2190
245
  for (CXXUnresolvedConstructExpr::arg_iterator Arg = Node->arg_begin(),
2191
245
                                             ArgEnd = Node->arg_end();
2192
256
       Arg != ArgEnd; 
++Arg11
) {
2193
11
    if (Arg != Node->arg_begin())
2194
0
      OS << ", ";
2195
11
    PrintExpr(*Arg);
2196
11
  }
2197
245
  OS << ")";
2198
245
}
2199
2200
void StmtPrinter::VisitCXXDependentScopeMemberExpr(
2201
2.11k
                                         CXXDependentScopeMemberExpr *Node) {
2202
2.11k
  if (!Node->isImplicitAccess()) {
2203
1.94k
    PrintExpr(Node->getBase());
2204
1.94k
    OS << (Node->isArrow() ? 
"->"590
:
"."1.35k
);
2205
1.94k
  }
2206
2.11k
  if (NestedNameSpecifier *Qualifier = Node->getQualifier())
2207
168
    Qualifier->print(OS, Policy);
2208
2.11k
  if (Node->hasTemplateKeyword())
2209
3
    OS << "template ";
2210
2.11k
  OS << Node->getMemberNameInfo();
2211
2.11k
  if (Node->hasExplicitTemplateArgs())
2212
2
    printTemplateArgumentList(OS, Node->template_arguments(), Policy);
2213
2.11k
}
2214
2215
8
void StmtPrinter::VisitUnresolvedMemberExpr(UnresolvedMemberExpr *Node) {
2216
8
  if (!Node->isImplicitAccess()) {
2217
8
    PrintExpr(Node->getBase());
2218
8
    OS << (Node->isArrow() ? 
"->"0
: ".");
2219
8
  }
2220
8
  if (NestedNameSpecifier *Qualifier = Node->getQualifier())
2221
0
    Qualifier->print(OS, Policy);
2222
8
  if (Node->hasTemplateKeyword())
2223
1
    OS << "template ";
2224
8
  OS << Node->getMemberNameInfo();
2225
8
  if (Node->hasExplicitTemplateArgs())
2226
8
    printTemplateArgumentList(OS, Node->template_arguments(), Policy);
2227
8
}
2228
2229
203
void StmtPrinter::VisitTypeTraitExpr(TypeTraitExpr *E) {
2230
203
  OS << getTraitSpelling(E->getTrait()) << "(";
2231
413
  for (unsigned I = 0, N = E->getNumArgs(); I != N; 
++I210
) {
2232
210
    if (I > 0)
2233
7
      OS << ", ";
2234
210
    E->getArg(I)->getType().print(OS, Policy);
2235
210
  }
2236
203
  OS << ")";
2237
203
}
2238
2239
0
void StmtPrinter::VisitArrayTypeTraitExpr(ArrayTypeTraitExpr *E) {
2240
0
  OS << getTraitSpelling(E->getTrait()) << '(';
2241
0
  E->getQueriedType().print(OS, Policy);
2242
0
  OS << ')';
2243
0
}
2244
2245
0
void StmtPrinter::VisitExpressionTraitExpr(ExpressionTraitExpr *E) {
2246
0
  OS << getTraitSpelling(E->getTrait()) << '(';
2247
0
  PrintExpr(E->getQueriedExpression());
2248
0
  OS << ')';
2249
0
}
2250
2251
0
void StmtPrinter::VisitCXXNoexceptExpr(CXXNoexceptExpr *E) {
2252
0
  OS << "noexcept(";
2253
0
  PrintExpr(E->getOperand());
2254
0
  OS << ")";
2255
0
}
2256
2257
580
void StmtPrinter::VisitPackExpansionExpr(PackExpansionExpr *E) {
2258
580
  PrintExpr(E->getPattern());
2259
580
  OS << "...";
2260
580
}
2261
2262
19
void StmtPrinter::VisitSizeOfPackExpr(SizeOfPackExpr *E) {
2263
19
  OS << "sizeof...(" << *E->getPack() << ")";
2264
19
}
2265
2266
void StmtPrinter::VisitSubstNonTypeTemplateParmPackExpr(
2267
5
                                       SubstNonTypeTemplateParmPackExpr *Node) {
2268
5
  OS << *Node->getParameterPack();
2269
5
}
2270
2271
void StmtPrinter::VisitSubstNonTypeTemplateParmExpr(
2272
1.80k
                                       SubstNonTypeTemplateParmExpr *Node) {
2273
1.80k
  Visit(Node->getReplacement());
2274
1.80k
}
2275
2276
0
void StmtPrinter::VisitFunctionParmPackExpr(FunctionParmPackExpr *E) {
2277
0
  OS << *E->getParameterPack();
2278
0
}
2279
2280
1.23k
void StmtPrinter::VisitMaterializeTemporaryExpr(MaterializeTemporaryExpr *Node){
2281
1.23k
  PrintExpr(Node->getSubExpr());
2282
1.23k
}
2283
2284
16
void StmtPrinter::VisitCXXFoldExpr(CXXFoldExpr *E) {
2285
16
  OS << "(";
2286
16
  if (E->getLHS()) {
2287
12
    PrintExpr(E->getLHS());
2288
12
    OS << " " << BinaryOperator::getOpcodeStr(E->getOperator()) << " ";
2289
12
  }
2290
16
  OS << "...";
2291
16
  if (E->getRHS()) {
2292
12
    OS << " " << BinaryOperator::getOpcodeStr(E->getOperator()) << " ";
2293
12
    PrintExpr(E->getRHS());
2294
12
  }
2295
16
  OS << ")";
2296
16
}
2297
2298
49
void StmtPrinter::VisitConceptSpecializationExpr(ConceptSpecializationExpr *E) {
2299
49
  NestedNameSpecifierLoc NNS = E->getNestedNameSpecifierLoc();
2300
49
  if (NNS)
2301
0
    NNS.getNestedNameSpecifier()->print(OS, Policy);
2302
49
  if (E->getTemplateKWLoc().isValid())
2303
0
    OS << "template ";
2304
49
  OS << E->getFoundDecl()->getName();
2305
49
  printTemplateArgumentList(OS, E->getTemplateArgsAsWritten()->arguments(),
2306
49
                            Policy,
2307
49
                            E->getNamedConcept()->getTemplateParameters());
2308
49
}
2309
2310
39
void StmtPrinter::VisitRequiresExpr(RequiresExpr *E) {
2311
39
  OS << "requires ";
2312
39
  auto LocalParameters = E->getLocalParameters();
2313
39
  if (!LocalParameters.empty()) {
2314
16
    OS << "(";
2315
17
    for (ParmVarDecl *LocalParam : LocalParameters) {
2316
17
      PrintRawDecl(LocalParam);
2317
17
      if (LocalParam != LocalParameters.back())
2318
1
        OS << ", ";
2319
17
    }
2320
2321
16
    OS << ") ";
2322
16
  }
2323
39
  OS << "{ ";
2324
39
  auto Requirements = E->getRequirements();
2325
59
  for (concepts::Requirement *Req : Requirements) {
2326
59
    if (auto *TypeReq = dyn_cast<concepts::TypeRequirement>(Req)) {
2327
15
      if (TypeReq->isSubstitutionFailure())
2328
4
        OS << "<<error-type>>";
2329
11
      else
2330
11
        TypeReq->getType()->getType().print(OS, Policy);
2331
44
    } else if (auto *ExprReq = dyn_cast<concepts::ExprRequirement>(Req)) {
2332
25
      if (ExprReq->isCompound())
2333
13
        OS << "{ ";
2334
25
      if (ExprReq->isExprSubstitutionFailure())
2335
2
        OS << "<<error-expression>>";
2336
23
      else
2337
23
        PrintExpr(ExprReq->getExpr());
2338
25
      if (ExprReq->isCompound()) {
2339
13
        OS << " }";
2340
13
        if (ExprReq->getNoexceptLoc().isValid())
2341
6
          OS << " noexcept";
2342
13
        const auto &RetReq = ExprReq->getReturnTypeRequirement();
2343
13
        if (!RetReq.isEmpty()) {
2344
11
          OS << " -> ";
2345
11
          if (RetReq.isSubstitutionFailure())
2346
1
            OS << "<<error-type>>";
2347
10
          else if (RetReq.isTypeConstraint())
2348
10
            RetReq.getTypeConstraint()->print(OS, Policy);
2349
11
        }
2350
13
      }
2351
25
    } else {
2352
19
      auto *NestedReq = cast<concepts::NestedRequirement>(Req);
2353
19
      OS << "requires ";
2354
19
      if (NestedReq->isSubstitutionFailure())
2355
1
        OS << "<<error-expression>>";
2356
18
      else
2357
18
        PrintExpr(NestedReq->getConstraintExpr());
2358
19
    }
2359
59
    OS << "; ";
2360
59
  }
2361
39
  OS << "}";
2362
39
}
2363
2364
// C++ Coroutines TS
2365
2366
0
void StmtPrinter::VisitCoroutineBodyStmt(CoroutineBodyStmt *S) {
2367
0
  Visit(S->getBody());
2368
0
}
2369
2370
1
void StmtPrinter::VisitCoreturnStmt(CoreturnStmt *S) {
2371
1
  OS << "co_return";
2372
1
  if (S->getOperand()) {
2373
1
    OS << " ";
2374
1
    Visit(S->getOperand());
2375
1
  }
2376
1
  OS << ";";
2377
1
}
2378
2379
0
void StmtPrinter::VisitCoawaitExpr(CoawaitExpr *S) {
2380
0
  OS << "co_await ";
2381
0
  PrintExpr(S->getOperand());
2382
0
}
2383
2384
0
void StmtPrinter::VisitDependentCoawaitExpr(DependentCoawaitExpr *S) {
2385
0
  OS << "co_await ";
2386
0
  PrintExpr(S->getOperand());
2387
0
}
2388
2389
0
void StmtPrinter::VisitCoyieldExpr(CoyieldExpr *S) {
2390
0
  OS << "co_yield ";
2391
0
  PrintExpr(S->getOperand());
2392
0
}
2393
2394
// Obj-C
2395
2396
4
void StmtPrinter::VisitObjCStringLiteral(ObjCStringLiteral *Node) {
2397
4
  OS << "@";
2398
4
  VisitStringLiteral(Node->getString());
2399
4
}
2400
2401
8
void StmtPrinter::VisitObjCBoxedExpr(ObjCBoxedExpr *E) {
2402
8
  OS << "@";
2403
8
  Visit(E->getSubExpr());
2404
8
}
2405
2406
1
void StmtPrinter::VisitObjCArrayLiteral(ObjCArrayLiteral *E) {
2407
1
  OS << "@[ ";
2408
1
  ObjCArrayLiteral::child_range Ch = E->children();
2409
3
  for (auto I = Ch.begin(), E = Ch.end(); I != E; 
++I2
) {
2410
2
    if (I != Ch.begin())
2411
1
      OS << ", ";
2412
2
    Visit(*I);
2413
2
  }
2414
1
  OS << " ]";
2415
1
}
2416
2417
3
void StmtPrinter::VisitObjCDictionaryLiteral(ObjCDictionaryLiteral *E) {
2418
3
  OS << "@{ ";
2419
8
  for (unsigned I = 0, N = E->getNumElements(); I != N; 
++I5
) {
2420
5
    if (I > 0)
2421
2
      OS << ", ";
2422
2423
5
    ObjCDictionaryElement Element = E->getKeyValueElement(I);
2424
5
    Visit(Element.Key);
2425
5
    OS << " : ";
2426
5
    Visit(Element.Value);
2427
5
    if (Element.isPackExpansion())
2428
1
      OS << "...";
2429
5
  }
2430
3
  OS << " }";
2431
3
}
2432
2433
6
void StmtPrinter::VisitObjCEncodeExpr(ObjCEncodeExpr *Node) {
2434
6
  OS << "@encode(";
2435
6
  Node->getEncodedType().print(OS, Policy);
2436
6
  OS << ')';
2437
6
}
2438
2439
0
void StmtPrinter::VisitObjCSelectorExpr(ObjCSelectorExpr *Node) {
2440
0
  OS << "@selector(";
2441
0
  Node->getSelector().print(OS);
2442
0
  OS << ')';
2443
0
}
2444
2445
0
void StmtPrinter::VisitObjCProtocolExpr(ObjCProtocolExpr *Node) {
2446
0
  OS << "@protocol(" << *Node->getProtocol() << ')';
2447
0
}
2448
2449
23
void StmtPrinter::VisitObjCMessageExpr(ObjCMessageExpr *Mess) {
2450
23
  OS << "[";
2451
23
  switch (Mess->getReceiverKind()) {
2452
19
  case ObjCMessageExpr::Instance:
2453
19
    PrintExpr(Mess->getInstanceReceiver());
2454
19
    break;
2455
2456
2
  case ObjCMessageExpr::Class:
2457
2
    Mess->getClassReceiver().print(OS, Policy);
2458
2
    break;
2459
2460
1
  case ObjCMessageExpr::SuperInstance:
2461
2
  case ObjCMessageExpr::SuperClass:
2462
2
    OS << "Super";
2463
2
    break;
2464
23
  }
2465
2466
23
  OS << ' ';
2467
23
  Selector selector = Mess->getSelector();
2468
23
  if (selector.isUnarySelector()) {
2469
19
    OS << selector.getNameForSlot(0);
2470
19
  } else {
2471
8
    for (unsigned i = 0, e = Mess->getNumArgs(); i != e; 
++i4
) {
2472
4
      if (i < selector.getNumArgs()) {
2473
4
        if (i > 0) 
OS << ' '0
;
2474
4
        if (selector.getIdentifierInfoForSlot(i))
2475
4
          OS << selector.getIdentifierInfoForSlot(i)->getName() << ':';
2476
0
        else
2477
0
           OS << ":";
2478
4
      }
2479
0
      else OS << ", "; // Handle variadic methods.
2480
2481
4
      PrintExpr(Mess->getArg(i));
2482
4
    }
2483
4
  }
2484
23
  OS << "]";
2485
23
}
2486
2487
0
void StmtPrinter::VisitObjCBoolLiteralExpr(ObjCBoolLiteralExpr *Node) {
2488
0
  OS << (Node->getValue() ? "__objc_yes" : "__objc_no");
2489
0
}
2490
2491
void
2492
0
StmtPrinter::VisitObjCIndirectCopyRestoreExpr(ObjCIndirectCopyRestoreExpr *E) {
2493
0
  PrintExpr(E->getSubExpr());
2494
0
}
2495
2496
void
2497
0
StmtPrinter::VisitObjCBridgedCastExpr(ObjCBridgedCastExpr *E) {
2498
0
  OS << '(' << E->getBridgeKindName();
2499
0
  E->getType().print(OS, Policy);
2500
0
  OS << ')';
2501
0
  PrintExpr(E->getSubExpr());
2502
0
}
2503
2504
10
void StmtPrinter::VisitBlockExpr(BlockExpr *Node) {
2505
10
  BlockDecl *BD = Node->getBlockDecl();
2506
10
  OS << "^";
2507
2508
10
  const FunctionType *AFT = Node->getFunctionType();
2509
2510
10
  if (isa<FunctionNoProtoType>(AFT)) {
2511
0
    OS << "()";
2512
10
  } else if (!BD->param_empty() || 
cast<FunctionProtoType>(AFT)->isVariadic()7
) {
2513
3
    OS << '(';
2514
3
    for (BlockDecl::param_iterator AI = BD->param_begin(),
2515
9
         E = BD->param_end(); AI != E; 
++AI6
) {
2516
6
      if (AI != BD->param_begin()) 
OS << ", "3
;
2517
6
      std::string ParamStr = (*AI)->getNameAsString();
2518
6
      (*AI)->getType().print(OS, Policy, ParamStr);
2519
6
    }
2520
2521
3
    const auto *FT = cast<FunctionProtoType>(AFT);
2522
3
    if (FT->isVariadic()) {
2523
0
      if (!BD->param_empty()) OS << ", ";
2524
0
      OS << "...";
2525
0
    }
2526
3
    OS << ')';
2527
3
  }
2528
10
  OS << "{ }";
2529
10
}
2530
2531
114
void StmtPrinter::VisitOpaqueValueExpr(OpaqueValueExpr *Node) {
2532
114
  PrintExpr(Node->getSourceExpr());
2533
114
}
2534
2535
0
void StmtPrinter::VisitTypoExpr(TypoExpr *Node) {
2536
  // TODO: Print something reasonable for a TypoExpr, if necessary.
2537
0
  llvm_unreachable("Cannot print TypoExpr nodes");
2538
0
}
2539
2540
27
void StmtPrinter::VisitRecoveryExpr(RecoveryExpr *Node) {
2541
27
  OS << "<recovery-expr>(";
2542
27
  const char *Sep = "";
2543
27
  for (Expr *E : Node->subExpressions()) {
2544
21
    OS << Sep;
2545
21
    PrintExpr(E);
2546
21
    Sep = ", ";
2547
21
  }
2548
27
  OS << ')';
2549
27
}
2550
2551
0
void StmtPrinter::VisitAsTypeExpr(AsTypeExpr *Node) {
2552
0
  OS << "__builtin_astype(";
2553
0
  PrintExpr(Node->getSrcExpr());
2554
0
  OS << ", ";
2555
0
  Node->getType().print(OS, Policy);
2556
0
  OS << ")";
2557
0
}
2558
2559
//===----------------------------------------------------------------------===//
2560
// Stmt method implementations
2561
//===----------------------------------------------------------------------===//
2562
2563
0
void Stmt::dumpPretty(const ASTContext &Context) const {
2564
0
  printPretty(llvm::errs(), nullptr, PrintingPolicy(Context.getLangOpts()));
2565
0
}
2566
2567
void Stmt::printPretty(raw_ostream &Out, PrinterHelper *Helper,
2568
                       const PrintingPolicy &Policy, unsigned Indentation,
2569
110k
                       StringRef NL, const ASTContext *Context) const {
2570
110k
  StmtPrinter P(Out, Helper, Policy, Indentation, NL, Context);
2571
110k
  P.Visit(const_cast<Stmt *>(this));
2572
110k
}
2573
2574
void Stmt::printJson(raw_ostream &Out, PrinterHelper *Helper,
2575
302
                     const PrintingPolicy &Policy, bool AddQuotes) const {
2576
302
  std::string Buf;
2577
302
  llvm::raw_string_ostream TempOut(Buf);
2578
2579
302
  printPretty(TempOut, Helper, Policy);
2580
2581
302
  Out << JsonFormat(TempOut.str(), AddQuotes);
2582
302
}
2583
2584
//===----------------------------------------------------------------------===//
2585
// PrinterHelper
2586
//===----------------------------------------------------------------------===//
2587
2588
// Implement virtual destructor.
2589
46.7k
PrinterHelper::~PrinterHelper() = default;