3226 lines · cpp
1//===--- TextNodeDumper.cpp - Printing of AST nodes -----------------------===//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-exception6//7//===----------------------------------------------------------------------===//8//9// This file implements AST dumping of components of individual AST nodes.10//11//===----------------------------------------------------------------------===//12 13#include "clang/AST/TextNodeDumper.h"14#include "clang/AST/APValue.h"15#include "clang/AST/DeclFriend.h"16#include "clang/AST/DeclOpenMP.h"17#include "clang/AST/DeclTemplate.h"18#include "clang/AST/LocInfoType.h"19#include "clang/AST/NestedNameSpecifier.h"20#include "clang/AST/Type.h"21#include "clang/AST/TypeLocVisitor.h"22#include "clang/Basic/Module.h"23#include "clang/Basic/SourceManager.h"24#include "clang/Basic/Specifiers.h"25#include "clang/Basic/TypeTraits.h"26#include "llvm/ADT/StringExtras.h"27#include "llvm/Frontend/HLSL/HLSLRootSignature.h"28 29#include <algorithm>30#include <utility>31 32using namespace clang;33 34static void dumpPreviousDeclImpl(raw_ostream &OS, ...) {}35 36template <typename T>37static void dumpPreviousDeclImpl(raw_ostream &OS, const Mergeable<T> *D) {38 const T *First = D->getFirstDecl();39 if (First != D)40 OS << " first " << First;41}42 43template <typename T>44static void dumpPreviousDeclImpl(raw_ostream &OS, const Redeclarable<T> *D) {45 const T *Prev = D->getPreviousDecl();46 if (Prev)47 OS << " prev " << Prev;48}49 50/// Dump the previous declaration in the redeclaration chain for a declaration,51/// if any.52static void dumpPreviousDecl(raw_ostream &OS, const Decl *D) {53 switch (D->getKind()) {54#define DECL(DERIVED, BASE) \55 case Decl::DERIVED: \56 return dumpPreviousDeclImpl(OS, cast<DERIVED##Decl>(D));57#define ABSTRACT_DECL(DECL)58#include "clang/AST/DeclNodes.inc"59 }60 llvm_unreachable("Decl that isn't part of DeclNodes.inc!");61}62 63TextNodeDumper::TextNodeDumper(raw_ostream &OS, const ASTContext &Context,64 bool ShowColors)65 : TextTreeStructure(OS, ShowColors), OS(OS), ShowColors(ShowColors),66 Context(&Context), SM(&Context.getSourceManager()),67 PrintPolicy(Context.getPrintingPolicy()),68 Traits(&Context.getCommentCommandTraits()) {}69 70TextNodeDumper::TextNodeDumper(raw_ostream &OS, bool ShowColors)71 : TextTreeStructure(OS, ShowColors), OS(OS), ShowColors(ShowColors) {}72 73void TextNodeDumper::Visit(const comments::Comment *C,74 const comments::FullComment *FC) {75 if (!C) {76 ColorScope Color(OS, ShowColors, NullColor);77 OS << "<<<NULL>>>";78 return;79 }80 81 {82 ColorScope Color(OS, ShowColors, CommentColor);83 OS << C->getCommentKindName();84 }85 dumpPointer(C);86 dumpSourceRange(C->getSourceRange());87 88 ConstCommentVisitor<TextNodeDumper, void,89 const comments::FullComment *>::visit(C, FC);90}91 92void TextNodeDumper::Visit(const Attr *A) {93 {94 ColorScope Color(OS, ShowColors, AttrColor);95 96 switch (A->getKind()) {97#define ATTR(X) \98 case attr::X: \99 OS << #X; \100 break;101#include "clang/Basic/AttrList.inc"102 }103 OS << "Attr";104 }105 dumpPointer(A);106 dumpSourceRange(A->getRange());107 if (A->isInherited())108 OS << " Inherited";109 if (A->isImplicit())110 OS << " Implicit";111 112 ConstAttrVisitor<TextNodeDumper>::Visit(A);113}114 115void TextNodeDumper::Visit(const TemplateArgument &TA, SourceRange R,116 const Decl *From, StringRef Label) {117 OS << "TemplateArgument";118 if (R.isValid())119 dumpSourceRange(R);120 121 if (From)122 dumpDeclRef(From, Label);123 124 ConstTemplateArgumentVisitor<TextNodeDumper>::Visit(TA);125}126 127void TextNodeDumper::Visit(const Stmt *Node) {128 if (!Node) {129 ColorScope Color(OS, ShowColors, NullColor);130 OS << "<<<NULL>>>";131 return;132 }133 {134 ColorScope Color(OS, ShowColors, StmtColor);135 OS << Node->getStmtClassName();136 }137 dumpPointer(Node);138 dumpSourceRange(Node->getSourceRange());139 140 if (const auto *E = dyn_cast<Expr>(Node)) {141 dumpType(E->getType());142 143 if (E->containsErrors()) {144 ColorScope Color(OS, ShowColors, ErrorsColor);145 OS << " contains-errors";146 }147 148 {149 ColorScope Color(OS, ShowColors, ValueKindColor);150 switch (E->getValueKind()) {151 case VK_PRValue:152 break;153 case VK_LValue:154 OS << " lvalue";155 break;156 case VK_XValue:157 OS << " xvalue";158 break;159 }160 }161 162 {163 ColorScope Color(OS, ShowColors, ObjectKindColor);164 switch (E->getObjectKind()) {165 case OK_Ordinary:166 break;167 case OK_BitField:168 OS << " bitfield";169 break;170 case OK_ObjCProperty:171 OS << " objcproperty";172 break;173 case OK_ObjCSubscript:174 OS << " objcsubscript";175 break;176 case OK_VectorComponent:177 OS << " vectorcomponent";178 break;179 case OK_MatrixComponent:180 OS << " matrixcomponent";181 break;182 }183 }184 }185 186 ConstStmtVisitor<TextNodeDumper>::Visit(Node);187}188 189void TextNodeDumper::Visit(const Type *T) {190 if (!T) {191 ColorScope Color(OS, ShowColors, NullColor);192 OS << "<<<NULL>>>";193 return;194 }195 if (isa<LocInfoType>(T)) {196 {197 ColorScope Color(OS, ShowColors, TypeColor);198 OS << "LocInfo Type";199 }200 dumpPointer(T);201 return;202 }203 204 {205 ColorScope Color(OS, ShowColors, TypeColor);206 OS << T->getTypeClassName() << "Type";207 }208 dumpPointer(T);209 OS << " ";210 dumpBareType(QualType(T, 0), false);211 212 QualType SingleStepDesugar =213 T->getLocallyUnqualifiedSingleStepDesugaredType();214 if (SingleStepDesugar != QualType(T, 0))215 OS << " sugar";216 217 if (T->containsErrors()) {218 ColorScope Color(OS, ShowColors, ErrorsColor);219 OS << " contains-errors";220 }221 222 if (T->isDependentType())223 OS << " dependent";224 else if (T->isInstantiationDependentType())225 OS << " instantiation_dependent";226 227 if (T->isVariablyModifiedType())228 OS << " variably_modified";229 if (T->containsUnexpandedParameterPack())230 OS << " contains_unexpanded_pack";231 if (T->isFromAST())232 OS << " imported";233 234 TypeVisitor<TextNodeDumper>::Visit(T);235}236 237void TextNodeDumper::Visit(QualType T) {238 OS << "QualType";239 dumpPointer(T.getAsOpaquePtr());240 OS << " ";241 dumpBareType(T, false);242 OS << " " << T.split().Quals.getAsString();243}244 245void TextNodeDumper::Visit(TypeLoc TL) {246 if (!TL) {247 ColorScope Color(OS, ShowColors, NullColor);248 OS << "<<<NULL>>>";249 return;250 }251 252 {253 ColorScope Color(OS, ShowColors, TypeColor);254 OS << (TL.getTypeLocClass() == TypeLoc::Qualified255 ? "Qualified"256 : TL.getType()->getTypeClassName())257 << "TypeLoc";258 }259 dumpSourceRange(TL.getSourceRange());260 OS << ' ';261 dumpBareType(TL.getType(), /*Desugar=*/false);262 263 TypeLocVisitor<TextNodeDumper>::Visit(TL);264}265 266void TextNodeDumper::Visit(const Decl *D) {267 if (!D) {268 ColorScope Color(OS, ShowColors, NullColor);269 OS << "<<<NULL>>>";270 return;271 }272 273 {274 ColorScope Color(OS, ShowColors, DeclKindNameColor);275 OS << D->getDeclKindName() << "Decl";276 }277 dumpPointer(D);278 if (D->getLexicalDeclContext() != D->getDeclContext())279 OS << " parent " << cast<Decl>(D->getDeclContext());280 dumpPreviousDecl(OS, D);281 dumpSourceRange(D->getSourceRange());282 OS << ' ';283 dumpLocation(D->getLocation());284 if (D->isFromASTFile())285 OS << " imported";286 if (Module *M = D->getOwningModule())287 OS << " in " << M->getFullModuleName();288 if (auto *ND = dyn_cast<NamedDecl>(D))289 for (Module *M : D->getASTContext().getModulesWithMergedDefinition(290 const_cast<NamedDecl *>(ND)))291 AddChild([=] { OS << "also in " << M->getFullModuleName(); });292 if (const NamedDecl *ND = dyn_cast<NamedDecl>(D))293 if (!ND->isUnconditionallyVisible())294 OS << " hidden";295 if (D->isImplicit())296 OS << " implicit";297 298 if (D->isUsed())299 OS << " used";300 else if (D->isThisDeclarationReferenced())301 OS << " referenced";302 303 if (D->isInvalidDecl())304 OS << " invalid";305 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) {306 if (FD->isConstexprSpecified())307 OS << " constexpr";308 if (FD->isConsteval())309 OS << " consteval";310 else if (FD->isImmediateFunction())311 OS << " immediate";312 if (FD->isMultiVersion())313 OS << " multiversion";314 }315 316 if (!isa<FunctionDecl>(*D)) {317 const auto *MD = dyn_cast<ObjCMethodDecl>(D);318 if (!MD || !MD->isThisDeclarationADefinition()) {319 const auto *DC = dyn_cast<DeclContext>(D);320 if (DC && DC->hasExternalLexicalStorage()) {321 ColorScope Color(OS, ShowColors, UndeserializedColor);322 OS << " <undeserialized declarations>";323 }324 }325 }326 327 switch (D->getFriendObjectKind()) {328 case Decl::FOK_None:329 break;330 case Decl::FOK_Declared:331 OS << " friend";332 break;333 case Decl::FOK_Undeclared:334 OS << " friend_undeclared";335 break;336 }337 338 ConstDeclVisitor<TextNodeDumper>::Visit(D);339}340 341void TextNodeDumper::Visit(const CXXCtorInitializer *Init) {342 OS << "CXXCtorInitializer";343 if (Init->isAnyMemberInitializer()) {344 OS << ' ';345 dumpBareDeclRef(Init->getAnyMember());346 } else if (Init->isBaseInitializer()) {347 dumpType(QualType(Init->getBaseClass(), 0));348 } else if (Init->isDelegatingInitializer()) {349 dumpType(Init->getTypeSourceInfo()->getType());350 } else {351 llvm_unreachable("Unknown initializer type");352 }353}354 355void TextNodeDumper::Visit(const BlockDecl::Capture &C) {356 OS << "capture";357 if (C.isByRef())358 OS << " byref";359 if (C.isNested())360 OS << " nested";361 if (C.getVariable()) {362 OS << ' ';363 dumpBareDeclRef(C.getVariable());364 }365}366 367void TextNodeDumper::Visit(const OMPClause *C) {368 if (!C) {369 ColorScope Color(OS, ShowColors, NullColor);370 OS << "<<<NULL>>> OMPClause";371 return;372 }373 {374 ColorScope Color(OS, ShowColors, AttrColor);375 StringRef ClauseName(llvm::omp::getOpenMPClauseName(C->getClauseKind()));376 OS << "OMP" << ClauseName.substr(/*Start=*/0, /*N=*/1).upper()377 << ClauseName.drop_front() << "Clause";378 }379 dumpPointer(C);380 dumpSourceRange(SourceRange(C->getBeginLoc(), C->getEndLoc()));381 if (C->isImplicit())382 OS << " <implicit>";383}384 385void TextNodeDumper::VisitOpenACCAsteriskSizeExpr(386 const OpenACCAsteriskSizeExpr *E) {387 // Nothing to do here, only location exists, and that is printed elsewhere.388}389 390void TextNodeDumper::Visit(const OpenACCClause *C) {391 if (!C) {392 ColorScope Color(OS, ShowColors, NullColor);393 OS << "<<<NULL>>> OpenACCClause";394 return;395 }396 {397 ColorScope Color(OS, ShowColors, AttrColor);398 OS << C->getClauseKind();399 400 // Handle clauses with parens for types that have no children, likely401 // because there is no sub expression.402 switch (C->getClauseKind()) {403 case OpenACCClauseKind::Default:404 OS << '(' << cast<OpenACCDefaultClause>(C)->getDefaultClauseKind() << ')';405 break;406 case OpenACCClauseKind::Async:407 case OpenACCClauseKind::Auto:408 case OpenACCClauseKind::Attach:409 case OpenACCClauseKind::Host:410 case OpenACCClauseKind::If:411 case OpenACCClauseKind::IfPresent:412 case OpenACCClauseKind::Independent:413 case OpenACCClauseKind::Detach:414 case OpenACCClauseKind::Delete:415 case OpenACCClauseKind::Device:416 case OpenACCClauseKind::DeviceNum:417 case OpenACCClauseKind::DefaultAsync:418 case OpenACCClauseKind::DeviceResident:419 case OpenACCClauseKind::DevicePtr:420 case OpenACCClauseKind::Finalize:421 case OpenACCClauseKind::FirstPrivate:422 case OpenACCClauseKind::Link:423 case OpenACCClauseKind::NoCreate:424 case OpenACCClauseKind::NoHost:425 case OpenACCClauseKind::NumGangs:426 case OpenACCClauseKind::NumWorkers:427 case OpenACCClauseKind::Present:428 case OpenACCClauseKind::Private:429 case OpenACCClauseKind::Self:430 case OpenACCClauseKind::Seq:431 case OpenACCClauseKind::Tile:432 case OpenACCClauseKind::Worker:433 case OpenACCClauseKind::UseDevice:434 case OpenACCClauseKind::Vector:435 case OpenACCClauseKind::VectorLength:436 case OpenACCClauseKind::Invalid:437 case OpenACCClauseKind::Shortloop:438 // The condition expression will be printed as a part of the 'children',439 // but print 'clause' here so it is clear what is happening from the dump.440 OS << " clause";441 break;442 case OpenACCClauseKind::Gang: {443 OS << " clause";444 // print the list of all GangKinds, so that there is some sort of445 // relationship to the expressions listed afterwards.446 auto *GC = cast<OpenACCGangClause>(C);447 448 for (unsigned I = 0; I < GC->getNumExprs(); ++I) {449 OS << " " << GC->getExpr(I).first;450 }451 break;452 }453 case OpenACCClauseKind::Collapse:454 OS << " clause";455 if (cast<OpenACCCollapseClause>(C)->hasForce())456 OS << ": force";457 break;458 459 case OpenACCClauseKind::Copy:460 case OpenACCClauseKind::PCopy:461 case OpenACCClauseKind::PresentOrCopy:462 OS << " clause";463 if (cast<OpenACCCopyClause>(C)->getModifierList() !=464 OpenACCModifierKind::Invalid)465 OS << " modifiers: " << cast<OpenACCCopyClause>(C)->getModifierList();466 break;467 case OpenACCClauseKind::CopyIn:468 case OpenACCClauseKind::PCopyIn:469 case OpenACCClauseKind::PresentOrCopyIn:470 OS << " clause";471 if (cast<OpenACCCopyInClause>(C)->getModifierList() !=472 OpenACCModifierKind::Invalid)473 OS << " modifiers: " << cast<OpenACCCopyInClause>(C)->getModifierList();474 break;475 case OpenACCClauseKind::CopyOut:476 case OpenACCClauseKind::PCopyOut:477 case OpenACCClauseKind::PresentOrCopyOut:478 OS << " clause";479 if (cast<OpenACCCopyOutClause>(C)->getModifierList() !=480 OpenACCModifierKind::Invalid)481 OS << " modifiers: "482 << cast<OpenACCCopyOutClause>(C)->getModifierList();483 break;484 case OpenACCClauseKind::Create:485 case OpenACCClauseKind::PCreate:486 case OpenACCClauseKind::PresentOrCreate:487 OS << " clause";488 if (cast<OpenACCCreateClause>(C)->getModifierList() !=489 OpenACCModifierKind::Invalid)490 OS << " modifiers: " << cast<OpenACCCreateClause>(C)->getModifierList();491 break;492 case OpenACCClauseKind::Wait:493 OS << " clause";494 if (cast<OpenACCWaitClause>(C)->hasDevNumExpr())495 OS << " has devnum";496 if (cast<OpenACCWaitClause>(C)->hasQueuesTag())497 OS << " has queues tag";498 break;499 case OpenACCClauseKind::DeviceType:500 case OpenACCClauseKind::DType:501 OS << "(";502 llvm::interleaveComma(503 cast<OpenACCDeviceTypeClause>(C)->getArchitectures(), OS,504 [&](const DeviceTypeArgument &Arch) {505 if (Arch.getIdentifierInfo() == nullptr)506 OS << "*";507 else508 OS << Arch.getIdentifierInfo()->getName();509 });510 OS << ")";511 break;512 case OpenACCClauseKind::Reduction:513 OS << " clause Operator: "514 << cast<OpenACCReductionClause>(C)->getReductionOp();515 break;516 case OpenACCClauseKind::Bind:517 OS << " clause";518 if (cast<OpenACCBindClause>(C)->isIdentifierArgument())519 OS << " identifier '"520 << cast<OpenACCBindClause>(C)->getIdentifierArgument()->getName()521 << "'";522 else523 AddChild(524 [=] { Visit(cast<OpenACCBindClause>(C)->getStringArgument()); });525 }526 }527 dumpPointer(C);528 dumpSourceRange(SourceRange(C->getBeginLoc(), C->getEndLoc()));529}530 531void TextNodeDumper::Visit(const GenericSelectionExpr::ConstAssociation &A) {532 const TypeSourceInfo *TSI = A.getTypeSourceInfo();533 if (TSI) {534 OS << "case ";535 dumpType(TSI->getType());536 } else {537 OS << "default";538 }539 540 if (A.isSelected())541 OS << " selected";542}543 544void TextNodeDumper::Visit(const ConceptReference *R) {545 if (!R) {546 ColorScope Color(OS, ShowColors, NullColor);547 OS << "<<<NULL>>> ConceptReference";548 return;549 }550 551 OS << "ConceptReference";552 dumpPointer(R);553 dumpSourceRange(R->getSourceRange());554 OS << ' ';555 dumpBareDeclRef(R->getNamedConcept());556}557 558void TextNodeDumper::Visit(const concepts::Requirement *R) {559 if (!R) {560 ColorScope Color(OS, ShowColors, NullColor);561 OS << "<<<NULL>>> Requirement";562 return;563 }564 565 {566 ColorScope Color(OS, ShowColors, StmtColor);567 switch (R->getKind()) {568 case concepts::Requirement::RK_Type:569 OS << "TypeRequirement";570 break;571 case concepts::Requirement::RK_Simple:572 OS << "SimpleRequirement";573 break;574 case concepts::Requirement::RK_Compound:575 OS << "CompoundRequirement";576 break;577 case concepts::Requirement::RK_Nested:578 OS << "NestedRequirement";579 break;580 }581 }582 583 dumpPointer(R);584 585 if (auto *ER = dyn_cast<concepts::ExprRequirement>(R)) {586 if (ER->hasNoexceptRequirement())587 OS << " noexcept";588 }589 590 if (R->isDependent())591 OS << " dependent";592 else593 OS << (R->isSatisfied() ? " satisfied" : " unsatisfied");594 if (R->containsUnexpandedParameterPack())595 OS << " contains_unexpanded_pack";596}597 598static double GetApproxValue(const llvm::APFloat &F) {599 llvm::APFloat V = F;600 bool ignored;601 V.convert(llvm::APFloat::IEEEdouble(), llvm::APFloat::rmNearestTiesToEven,602 &ignored);603 return V.convertToDouble();604}605 606/// True if the \p APValue \p Value can be folded onto the current line.607static bool isSimpleAPValue(const APValue &Value) {608 switch (Value.getKind()) {609 case APValue::None:610 case APValue::Indeterminate:611 case APValue::Int:612 case APValue::Float:613 case APValue::FixedPoint:614 case APValue::ComplexInt:615 case APValue::ComplexFloat:616 case APValue::LValue:617 case APValue::MemberPointer:618 case APValue::AddrLabelDiff:619 return true;620 case APValue::Vector:621 case APValue::Array:622 case APValue::Struct:623 return false;624 case APValue::Union:625 return isSimpleAPValue(Value.getUnionValue());626 }627 llvm_unreachable("unexpected APValue kind!");628}629 630/// Dump the children of the \p APValue \p Value.631///632/// \param[in] Value The \p APValue to visit633/// \param[in] Ty The \p QualType passed to \p Visit634///635/// \param[in] IdxToChildFun A function mapping an \p APValue and an index636/// to one of the child of the \p APValue637///638/// \param[in] NumChildren \p IdxToChildFun will be called on \p Value with639/// the indices in the range \p [0,NumChildren(640///641/// \param[in] LabelSingular The label to use on a line with a single child642/// \param[in] LabelPlurial The label to use on a line with multiple children643void TextNodeDumper::dumpAPValueChildren(644 const APValue &Value, QualType Ty,645 const APValue &(*IdxToChildFun)(const APValue &, unsigned),646 unsigned NumChildren, StringRef LabelSingular, StringRef LabelPlurial) {647 // To save some vertical space we print up to MaxChildrenPerLine APValues648 // considered to be simple (by isSimpleAPValue) on a single line.649 constexpr unsigned MaxChildrenPerLine = 4;650 unsigned I = 0;651 while (I < NumChildren) {652 unsigned J = I;653 while (J < NumChildren) {654 if (isSimpleAPValue(IdxToChildFun(Value, J)) &&655 (J - I < MaxChildrenPerLine)) {656 ++J;657 continue;658 }659 break;660 }661 662 J = std::max(I + 1, J);663 664 // Print [I,J) on a single line.665 AddChild(J - I > 1 ? LabelPlurial : LabelSingular, [=]() {666 for (unsigned X = I; X < J; ++X) {667 Visit(IdxToChildFun(Value, X), Ty);668 if (X + 1 != J)669 OS << ", ";670 }671 });672 I = J;673 }674}675 676void TextNodeDumper::Visit(const APValue &Value, QualType Ty) {677 ColorScope Color(OS, ShowColors, ValueKindColor);678 switch (Value.getKind()) {679 case APValue::None:680 OS << "None";681 return;682 case APValue::Indeterminate:683 OS << "Indeterminate";684 return;685 case APValue::Int:686 OS << "Int ";687 {688 ColorScope Color(OS, ShowColors, ValueColor);689 OS << Value.getInt();690 }691 return;692 case APValue::Float:693 OS << "Float ";694 {695 ColorScope Color(OS, ShowColors, ValueColor);696 OS << GetApproxValue(Value.getFloat());697 }698 return;699 case APValue::FixedPoint:700 OS << "FixedPoint ";701 {702 ColorScope Color(OS, ShowColors, ValueColor);703 OS << Value.getFixedPoint();704 }705 return;706 case APValue::Vector: {707 unsigned VectorLength = Value.getVectorLength();708 OS << "Vector length=" << VectorLength;709 710 dumpAPValueChildren(711 Value, Ty,712 [](const APValue &Value, unsigned Index) -> const APValue & {713 return Value.getVectorElt(Index);714 },715 VectorLength, "element", "elements");716 return;717 }718 case APValue::ComplexInt:719 OS << "ComplexInt ";720 {721 ColorScope Color(OS, ShowColors, ValueColor);722 OS << Value.getComplexIntReal() << " + " << Value.getComplexIntImag()723 << 'i';724 }725 return;726 case APValue::ComplexFloat:727 OS << "ComplexFloat ";728 {729 ColorScope Color(OS, ShowColors, ValueColor);730 OS << GetApproxValue(Value.getComplexFloatReal()) << " + "731 << GetApproxValue(Value.getComplexFloatImag()) << 'i';732 }733 return;734 case APValue::LValue: {735 (void)Context;736 OS << "LValue Base=";737 APValue::LValueBase B = Value.getLValueBase();738 if (B.isNull())739 OS << "null";740 else if (const auto *BE = B.dyn_cast<const Expr *>()) {741 OS << BE->getStmtClassName() << ' ';742 dumpPointer(BE);743 } else if (const auto BTI = B.dyn_cast<TypeInfoLValue>()) {744 OS << "TypeInfoLValue ";745 ColorScope Color(OS, ShowColors, TypeColor);746 BTI.print(OS, PrintPolicy);747 } else if (B.is<DynamicAllocLValue>()) {748 OS << "DynamicAllocLValue";749 auto BDA = B.getDynamicAllocType();750 dumpType(BDA);751 } else {752 const auto *VDB = B.get<const ValueDecl *>();753 OS << VDB->getDeclKindName() << "Decl";754 dumpPointer(VDB);755 }756 OS << ", Null=" << Value.isNullPointer()757 << ", Offset=" << Value.getLValueOffset().getQuantity()758 << ", HasPath=" << Value.hasLValuePath();759 if (Value.hasLValuePath()) {760 OS << ", PathLength=" << Value.getLValuePath().size();761 OS << ", Path=(";762 llvm::ListSeparator Sep;763 for (const auto &PathEntry : Value.getLValuePath()) {764 // We're printing all entries as array indices because don't have the765 // type information here to do anything else.766 OS << Sep << PathEntry.getAsArrayIndex();767 }768 OS << ")";769 }770 return;771 }772 case APValue::Array: {773 unsigned ArraySize = Value.getArraySize();774 unsigned NumInitializedElements = Value.getArrayInitializedElts();775 OS << "Array size=" << ArraySize;776 777 dumpAPValueChildren(778 Value, Ty,779 [](const APValue &Value, unsigned Index) -> const APValue & {780 return Value.getArrayInitializedElt(Index);781 },782 NumInitializedElements, "element", "elements");783 784 if (Value.hasArrayFiller()) {785 AddChild("filler", [=] {786 {787 ColorScope Color(OS, ShowColors, ValueColor);788 OS << ArraySize - NumInitializedElements << " x ";789 }790 Visit(Value.getArrayFiller(), Ty);791 });792 }793 794 return;795 }796 case APValue::Struct: {797 OS << "Struct";798 799 dumpAPValueChildren(800 Value, Ty,801 [](const APValue &Value, unsigned Index) -> const APValue & {802 return Value.getStructBase(Index);803 },804 Value.getStructNumBases(), "base", "bases");805 806 dumpAPValueChildren(807 Value, Ty,808 [](const APValue &Value, unsigned Index) -> const APValue & {809 return Value.getStructField(Index);810 },811 Value.getStructNumFields(), "field", "fields");812 813 return;814 }815 case APValue::Union: {816 OS << "Union";817 {818 ColorScope Color(OS, ShowColors, ValueColor);819 if (const FieldDecl *FD = Value.getUnionField())820 OS << " ." << *cast<NamedDecl>(FD);821 }822 // If the union value is considered to be simple, fold it into the823 // current line to save some vertical space.824 const APValue &UnionValue = Value.getUnionValue();825 if (isSimpleAPValue(UnionValue)) {826 OS << ' ';827 Visit(UnionValue, Ty);828 } else {829 AddChild([=] { Visit(UnionValue, Ty); });830 }831 832 return;833 }834 case APValue::MemberPointer: {835 OS << "MemberPointer ";836 auto Path = Value.getMemberPointerPath();837 for (const CXXRecordDecl *D : Path) {838 {839 ColorScope Color(OS, ShowColors, DeclNameColor);840 OS << D->getDeclName();841 }842 OS << "::";843 }844 845 ColorScope Color(OS, ShowColors, DeclNameColor);846 if (const ValueDecl *MemDecl = Value.getMemberPointerDecl())847 OS << MemDecl->getDeclName();848 else849 OS << "null";850 return;851 }852 case APValue::AddrLabelDiff:853 OS << "AddrLabelDiff ";854 OS << "&&" << Value.getAddrLabelDiffLHS()->getLabel()->getName();855 OS << " - ";856 OS << "&&" << Value.getAddrLabelDiffRHS()->getLabel()->getName();857 return;858 }859 llvm_unreachable("Unknown APValue kind!");860}861 862void TextNodeDumper::dumpPointer(const void *Ptr) {863 ColorScope Color(OS, ShowColors, AddressColor);864 OS << ' ' << Ptr;865}866 867void TextNodeDumper::dumpLocation(SourceLocation Loc) {868 if (!SM)869 return;870 871 ColorScope Color(OS, ShowColors, LocationColor);872 SourceLocation SpellingLoc = SM->getSpellingLoc(Loc);873 874 // The general format we print out is filename:line:col, but we drop pieces875 // that haven't changed since the last loc printed.876 PresumedLoc PLoc = SM->getPresumedLoc(SpellingLoc);877 878 if (PLoc.isInvalid()) {879 OS << "<invalid sloc>";880 return;881 }882 883 if (strcmp(PLoc.getFilename(), LastLocFilename) != 0) {884 OS << PLoc.getFilename() << ':' << PLoc.getLine() << ':'885 << PLoc.getColumn();886 LastLocFilename = PLoc.getFilename();887 LastLocLine = PLoc.getLine();888 } else if (PLoc.getLine() != LastLocLine) {889 OS << "line" << ':' << PLoc.getLine() << ':' << PLoc.getColumn();890 LastLocLine = PLoc.getLine();891 } else {892 OS << "col" << ':' << PLoc.getColumn();893 }894}895 896void TextNodeDumper::dumpSourceRange(SourceRange R) {897 // Can't translate locations if a SourceManager isn't available.898 if (!SM)899 return;900 901 OS << " <";902 dumpLocation(R.getBegin());903 if (R.getBegin() != R.getEnd()) {904 OS << ", ";905 dumpLocation(R.getEnd());906 }907 OS << ">";908 909 // <t2.c:123:421[blah], t2.c:412:321>910}911 912void TextNodeDumper::dumpBareType(QualType T, bool Desugar) {913 ColorScope Color(OS, ShowColors, TypeColor);914 915 SplitQualType T_split = T.split();916 std::string T_str = QualType::getAsString(T_split, PrintPolicy);917 OS << "'" << T_str << "'";918 919 if (Desugar && !T.isNull()) {920 // If the type is sugared, also dump a (shallow) desugared type when921 // it is visibly different.922 SplitQualType D_split = T.getSplitDesugaredType();923 if (T_split != D_split) {924 std::string D_str = QualType::getAsString(D_split, PrintPolicy);925 if (T_str != D_str)926 OS << ":'" << QualType::getAsString(D_split, PrintPolicy) << "'";927 }928 }929}930 931void TextNodeDumper::dumpType(QualType T) {932 OS << ' ';933 dumpBareType(T);934}935 936void TextNodeDumper::dumpBareDeclRef(const Decl *D) {937 if (!D) {938 ColorScope Color(OS, ShowColors, NullColor);939 OS << "<<<NULL>>>";940 return;941 }942 943 {944 ColorScope Color(OS, ShowColors, DeclKindNameColor);945 OS << D->getDeclKindName();946 }947 dumpPointer(D);948 949 if (const NamedDecl *ND = dyn_cast<NamedDecl>(D)) {950 ColorScope Color(OS, ShowColors, DeclNameColor);951 if (DeclarationName Name = ND->getDeclName())952 OS << " '" << Name << '\'';953 else954 switch (ND->getKind()) {955 case Decl::Decomposition: {956 auto *DD = cast<DecompositionDecl>(ND);957 OS << " first_binding '" << DD->bindings()[0]->getDeclName() << '\'';958 break;959 }960 case Decl::Field: {961 auto *FD = cast<FieldDecl>(ND);962 OS << " field_index " << FD->getFieldIndex();963 break;964 }965 case Decl::ParmVar: {966 auto *PD = cast<ParmVarDecl>(ND);967 OS << " depth " << PD->getFunctionScopeDepth() << " index "968 << PD->getFunctionScopeIndex();969 break;970 }971 case Decl::TemplateTypeParm: {972 auto *TD = cast<TemplateTypeParmDecl>(ND);973 OS << " depth " << TD->getDepth() << " index " << TD->getIndex();974 break;975 }976 case Decl::NonTypeTemplateParm: {977 auto *TD = cast<NonTypeTemplateParmDecl>(ND);978 OS << " depth " << TD->getDepth() << " index " << TD->getIndex();979 break;980 }981 default:982 // Var, Namespace, (CXX)Record: Nothing else besides source location.983 dumpSourceRange(ND->getSourceRange());984 break;985 }986 }987 988 if (const ValueDecl *VD = dyn_cast<ValueDecl>(D))989 dumpType(VD->getType());990}991 992void TextNodeDumper::dumpName(const NamedDecl *ND) {993 if (ND->getDeclName()) {994 ColorScope Color(OS, ShowColors, DeclNameColor);995 OS << ' ' << ND->getDeclName();996 }997}998 999void TextNodeDumper::dumpAccessSpecifier(AccessSpecifier AS) {1000 const auto AccessSpelling = getAccessSpelling(AS);1001 if (AccessSpelling.empty())1002 return;1003 OS << AccessSpelling;1004}1005 1006void TextNodeDumper::dumpCleanupObject(1007 const ExprWithCleanups::CleanupObject &C) {1008 if (auto *BD = dyn_cast<BlockDecl *>(C))1009 dumpDeclRef(BD, "cleanup");1010 else if (auto *CLE = dyn_cast<CompoundLiteralExpr *>(C))1011 AddChild([=] {1012 OS << "cleanup ";1013 {1014 ColorScope Color(OS, ShowColors, StmtColor);1015 OS << CLE->getStmtClassName();1016 }1017 dumpPointer(CLE);1018 });1019 else1020 llvm_unreachable("unexpected cleanup type");1021}1022 1023void clang::TextNodeDumper::dumpTemplateSpecializationKind(1024 TemplateSpecializationKind TSK) {1025 switch (TSK) {1026 case TSK_Undeclared:1027 break;1028 case TSK_ImplicitInstantiation:1029 OS << " implicit_instantiation";1030 break;1031 case TSK_ExplicitSpecialization:1032 OS << " explicit_specialization";1033 break;1034 case TSK_ExplicitInstantiationDeclaration:1035 OS << " explicit_instantiation_declaration";1036 break;1037 case TSK_ExplicitInstantiationDefinition:1038 OS << " explicit_instantiation_definition";1039 break;1040 }1041}1042 1043void clang::TextNodeDumper::dumpNestedNameSpecifier(NestedNameSpecifier NNS) {1044 if (!NNS)1045 return;1046 1047 AddChild([=] {1048 OS << "NestedNameSpecifier";1049 1050 switch (NNS.getKind()) {1051 case NestedNameSpecifier::Kind::Namespace: {1052 auto [Namespace, Prefix] = NNS.getAsNamespaceAndPrefix();1053 OS << " "; // "Namespace" is printed as the decl kind.1054 dumpBareDeclRef(Namespace);1055 dumpNestedNameSpecifier(Prefix);1056 break;1057 }1058 case NestedNameSpecifier::Kind::Type:1059 OS << " TypeSpec";1060 dumpType(QualType(NNS.getAsType(), 0));1061 break;1062 case NestedNameSpecifier::Kind::Global:1063 OS << " Global";1064 break;1065 case NestedNameSpecifier::Kind::MicrosoftSuper:1066 OS << " Super";1067 break;1068 case NestedNameSpecifier::Kind::Null:1069 llvm_unreachable("unexpected null nested name specifier");1070 }1071 });1072}1073 1074void TextNodeDumper::dumpDeclRef(const Decl *D, StringRef Label) {1075 if (!D)1076 return;1077 1078 AddChild([=] {1079 if (!Label.empty())1080 OS << Label << ' ';1081 dumpBareDeclRef(D);1082 });1083}1084 1085void TextNodeDumper::dumpTemplateArgument(const TemplateArgument &TA) {1086 llvm::SmallString<128> Str;1087 {1088 llvm::raw_svector_ostream SS(Str);1089 TA.print(PrintPolicy, SS, /*IncludeType=*/true);1090 }1091 OS << " '" << Str << "'";1092 1093 if (!Context)1094 return;1095 1096 if (TemplateArgument CanonTA = Context->getCanonicalTemplateArgument(TA);1097 !CanonTA.structurallyEquals(TA)) {1098 llvm::SmallString<128> CanonStr;1099 {1100 llvm::raw_svector_ostream SS(CanonStr);1101 CanonTA.print(PrintPolicy, SS, /*IncludeType=*/true);1102 }1103 if (CanonStr != Str)1104 OS << ":'" << CanonStr << "'";1105 }1106}1107 1108const char *TextNodeDumper::getCommandName(unsigned CommandID) {1109 if (Traits)1110 return Traits->getCommandInfo(CommandID)->Name;1111 const comments::CommandInfo *Info =1112 comments::CommandTraits::getBuiltinCommandInfo(CommandID);1113 if (Info)1114 return Info->Name;1115 return "<not a builtin command>";1116}1117 1118void TextNodeDumper::printFPOptions(FPOptionsOverride FPO) {1119#define FP_OPTION(NAME, TYPE, WIDTH, PREVIOUS) \1120 if (FPO.has##NAME##Override()) \1121 OS << " " #NAME "=" << FPO.get##NAME##Override();1122#include "clang/Basic/FPOptions.def"1123}1124 1125void TextNodeDumper::visitTextComment(const comments::TextComment *C,1126 const comments::FullComment *) {1127 OS << " Text=\"" << C->getText() << "\"";1128}1129 1130void TextNodeDumper::visitInlineCommandComment(1131 const comments::InlineCommandComment *C, const comments::FullComment *) {1132 OS << " Name=\"" << getCommandName(C->getCommandID()) << "\"";1133 switch (C->getRenderKind()) {1134 case comments::InlineCommandRenderKind::Normal:1135 OS << " RenderNormal";1136 break;1137 case comments::InlineCommandRenderKind::Bold:1138 OS << " RenderBold";1139 break;1140 case comments::InlineCommandRenderKind::Monospaced:1141 OS << " RenderMonospaced";1142 break;1143 case comments::InlineCommandRenderKind::Emphasized:1144 OS << " RenderEmphasized";1145 break;1146 case comments::InlineCommandRenderKind::Anchor:1147 OS << " RenderAnchor";1148 break;1149 }1150 1151 for (unsigned i = 0, e = C->getNumArgs(); i != e; ++i)1152 OS << " Arg[" << i << "]=\"" << C->getArgText(i) << "\"";1153}1154 1155void TextNodeDumper::visitHTMLStartTagComment(1156 const comments::HTMLStartTagComment *C, const comments::FullComment *) {1157 OS << " Name=\"" << C->getTagName() << "\"";1158 if (C->getNumAttrs() != 0) {1159 OS << " Attrs: ";1160 for (unsigned i = 0, e = C->getNumAttrs(); i != e; ++i) {1161 const comments::HTMLStartTagComment::Attribute &Attr = C->getAttr(i);1162 OS << " \"" << Attr.Name << "=\"" << Attr.Value << "\"";1163 }1164 }1165 if (C->isSelfClosing())1166 OS << " SelfClosing";1167}1168 1169void TextNodeDumper::visitHTMLEndTagComment(1170 const comments::HTMLEndTagComment *C, const comments::FullComment *) {1171 OS << " Name=\"" << C->getTagName() << "\"";1172}1173 1174void TextNodeDumper::visitBlockCommandComment(1175 const comments::BlockCommandComment *C, const comments::FullComment *) {1176 OS << " Name=\"" << getCommandName(C->getCommandID()) << "\"";1177 for (unsigned i = 0, e = C->getNumArgs(); i != e; ++i)1178 OS << " Arg[" << i << "]=\"" << C->getArgText(i) << "\"";1179}1180 1181void TextNodeDumper::visitParamCommandComment(1182 const comments::ParamCommandComment *C, const comments::FullComment *FC) {1183 OS << " "1184 << comments::ParamCommandComment::getDirectionAsString(C->getDirection());1185 1186 if (C->isDirectionExplicit())1187 OS << " explicitly";1188 else1189 OS << " implicitly";1190 1191 if (C->hasParamName()) {1192 if (C->isParamIndexValid())1193 OS << " Param=\"" << C->getParamName(FC) << "\"";1194 else1195 OS << " Param=\"" << C->getParamNameAsWritten() << "\"";1196 }1197 1198 if (C->isParamIndexValid() && !C->isVarArgParam())1199 OS << " ParamIndex=" << C->getParamIndex();1200}1201 1202void TextNodeDumper::visitTParamCommandComment(1203 const comments::TParamCommandComment *C, const comments::FullComment *FC) {1204 if (C->hasParamName()) {1205 if (C->isPositionValid())1206 OS << " Param=\"" << C->getParamName(FC) << "\"";1207 else1208 OS << " Param=\"" << C->getParamNameAsWritten() << "\"";1209 }1210 1211 if (C->isPositionValid()) {1212 OS << " Position=<";1213 for (unsigned i = 0, e = C->getDepth(); i != e; ++i) {1214 OS << C->getIndex(i);1215 if (i != e - 1)1216 OS << ", ";1217 }1218 OS << ">";1219 }1220}1221 1222void TextNodeDumper::visitVerbatimBlockComment(1223 const comments::VerbatimBlockComment *C, const comments::FullComment *) {1224 OS << " Name=\"" << getCommandName(C->getCommandID())1225 << "\""1226 " CloseName=\""1227 << C->getCloseName() << "\"";1228}1229 1230void TextNodeDumper::visitVerbatimBlockLineComment(1231 const comments::VerbatimBlockLineComment *C,1232 const comments::FullComment *) {1233 OS << " Text=\"" << C->getText() << "\"";1234}1235 1236void TextNodeDumper::visitVerbatimLineComment(1237 const comments::VerbatimLineComment *C, const comments::FullComment *) {1238 OS << " Text=\"" << C->getText() << "\"";1239}1240 1241void TextNodeDumper::VisitNullTemplateArgument(const TemplateArgument &) {1242 OS << " null";1243}1244 1245void TextNodeDumper::VisitTypeTemplateArgument(const TemplateArgument &TA) {1246 OS << " type";1247 dumpTemplateArgument(TA);1248}1249 1250void TextNodeDumper::VisitDeclarationTemplateArgument(1251 const TemplateArgument &TA) {1252 OS << " decl";1253 dumpTemplateArgument(TA);1254 dumpDeclRef(TA.getAsDecl());1255}1256 1257void TextNodeDumper::VisitNullPtrTemplateArgument(const TemplateArgument &TA) {1258 OS << " nullptr";1259 dumpTemplateArgument(TA);1260}1261 1262void TextNodeDumper::VisitIntegralTemplateArgument(const TemplateArgument &TA) {1263 OS << " integral";1264 dumpTemplateArgument(TA);1265}1266 1267void TextNodeDumper::VisitStructuralValueTemplateArgument(1268 const TemplateArgument &TA) {1269 OS << " structural value";1270 dumpTemplateArgument(TA);1271}1272 1273void TextNodeDumper::dumpTemplateName(TemplateName TN, StringRef Label) {1274 AddChild(Label, [=] {1275 {1276 llvm::SmallString<128> Str;1277 {1278 llvm::raw_svector_ostream SS(Str);1279 TN.print(SS, PrintPolicy);1280 }1281 OS << "'" << Str << "'";1282 1283 if (Context) {1284 if (TemplateName CanonTN = Context->getCanonicalTemplateName(TN);1285 CanonTN != TN) {1286 llvm::SmallString<128> CanonStr;1287 {1288 llvm::raw_svector_ostream SS(CanonStr);1289 CanonTN.print(SS, PrintPolicy);1290 }1291 if (CanonStr != Str)1292 OS << ":'" << CanonStr << "'";1293 }1294 }1295 }1296 dumpBareTemplateName(TN);1297 });1298}1299 1300void TextNodeDumper::dumpBareTemplateName(TemplateName TN) {1301 switch (TN.getKind()) {1302 case TemplateName::Template:1303 AddChild([=] { Visit(TN.getAsTemplateDecl()); });1304 return;1305 case TemplateName::UsingTemplate: {1306 const UsingShadowDecl *USD = TN.getAsUsingShadowDecl();1307 AddChild([=] { Visit(USD); });1308 AddChild("target", [=] { Visit(USD->getTargetDecl()); });1309 return;1310 }1311 case TemplateName::QualifiedTemplate: {1312 OS << " qualified";1313 const QualifiedTemplateName *QTN = TN.getAsQualifiedTemplateName();1314 if (QTN->hasTemplateKeyword())1315 OS << " keyword";1316 dumpNestedNameSpecifier(QTN->getQualifier());1317 dumpBareTemplateName(QTN->getUnderlyingTemplate());1318 return;1319 }1320 case TemplateName::DependentTemplate: {1321 OS << " dependent";1322 const DependentTemplateName *DTN = TN.getAsDependentTemplateName();1323 dumpNestedNameSpecifier(DTN->getQualifier());1324 return;1325 }1326 case TemplateName::SubstTemplateTemplateParm: {1327 OS << " subst";1328 const SubstTemplateTemplateParmStorage *STS =1329 TN.getAsSubstTemplateTemplateParm();1330 OS << " index " << STS->getIndex();1331 if (UnsignedOrNone PackIndex = STS->getPackIndex())1332 OS << " pack_index " << *PackIndex;1333 if (STS->getFinal())1334 OS << " final";1335 if (const TemplateTemplateParmDecl *P = STS->getParameter())1336 AddChild("parameter", [=] { Visit(P); });1337 dumpDeclRef(STS->getAssociatedDecl(), "associated");1338 dumpTemplateName(STS->getReplacement(), "replacement");1339 return;1340 }1341 case TemplateName::DeducedTemplate: {1342 OS << " deduced";1343 const DeducedTemplateStorage *DTS = TN.getAsDeducedTemplateName();1344 dumpTemplateName(DTS->getUnderlying(), "underlying");1345 AddChild("defaults", [=] {1346 auto [StartPos, Args] = DTS->getDefaultArguments();1347 OS << " start " << StartPos;1348 for (const TemplateArgument &Arg : Args)1349 AddChild([=] { Visit(Arg, SourceRange()); });1350 });1351 return;1352 }1353 // FIXME: Implement these.1354 case TemplateName::OverloadedTemplate:1355 OS << " overloaded";1356 return;1357 case TemplateName::AssumedTemplate:1358 OS << " assumed";1359 return;1360 case TemplateName::SubstTemplateTemplateParmPack:1361 OS << " subst_pack";1362 return;1363 }1364 llvm_unreachable("Unexpected TemplateName Kind");1365}1366 1367void TextNodeDumper::VisitTemplateTemplateArgument(const TemplateArgument &TA) {1368 OS << " template";1369 dumpTemplateArgument(TA);1370 dumpBareTemplateName(TA.getAsTemplate());1371}1372 1373void TextNodeDumper::VisitTemplateExpansionTemplateArgument(1374 const TemplateArgument &TA) {1375 OS << " template expansion";1376 dumpTemplateArgument(TA);1377 dumpBareTemplateName(TA.getAsTemplateOrTemplatePattern());1378}1379 1380void TextNodeDumper::VisitExpressionTemplateArgument(1381 const TemplateArgument &TA) {1382 OS << " expr";1383 if (TA.isCanonicalExpr())1384 OS << " canonical";1385 dumpTemplateArgument(TA);1386}1387 1388void TextNodeDumper::VisitPackTemplateArgument(const TemplateArgument &TA) {1389 OS << " pack";1390 dumpTemplateArgument(TA);1391}1392 1393static void dumpBasePath(raw_ostream &OS, const CastExpr *Node) {1394 if (Node->path_empty())1395 return;1396 1397 OS << " (";1398 bool First = true;1399 for (CastExpr::path_const_iterator I = Node->path_begin(),1400 E = Node->path_end();1401 I != E; ++I) {1402 const CXXBaseSpecifier *Base = *I;1403 if (!First)1404 OS << " -> ";1405 1406 const auto *RD = cast<CXXRecordDecl>(1407 Base->getType()->castAsCanonical<RecordType>()->getDecl());1408 1409 if (Base->isVirtual())1410 OS << "virtual ";1411 OS << RD->getName();1412 First = false;1413 }1414 1415 OS << ')';1416}1417 1418void TextNodeDumper::VisitLoopControlStmt(const LoopControlStmt *Node) {1419 if (!Node->hasLabelTarget())1420 return;1421 1422 OS << " '" << Node->getLabelDecl()->getIdentifier()->getName() << "' (";1423 1424 auto *Target = Node->getNamedLoopOrSwitch();1425 if (!Target) {1426 ColorScope Color(OS, ShowColors, NullColor);1427 OS << "<<<NULL>>>";1428 } else {1429 {1430 ColorScope Color(OS, ShowColors, StmtColor);1431 OS << Target->getStmtClassName();1432 }1433 dumpPointer(Target);1434 }1435 OS << ")";1436}1437 1438void TextNodeDumper::VisitIfStmt(const IfStmt *Node) {1439 if (Node->hasInitStorage())1440 OS << " has_init";1441 if (Node->hasVarStorage())1442 OS << " has_var";1443 if (Node->hasElseStorage())1444 OS << " has_else";1445 if (Node->isConstexpr())1446 OS << " constexpr";1447 if (Node->isConsteval()) {1448 OS << " ";1449 if (Node->isNegatedConsteval())1450 OS << "!";1451 OS << "consteval";1452 }1453}1454 1455void TextNodeDumper::VisitSwitchStmt(const SwitchStmt *Node) {1456 if (Node->hasInitStorage())1457 OS << " has_init";1458 if (Node->hasVarStorage())1459 OS << " has_var";1460}1461 1462void TextNodeDumper::VisitWhileStmt(const WhileStmt *Node) {1463 if (Node->hasVarStorage())1464 OS << " has_var";1465}1466 1467void TextNodeDumper::VisitLabelStmt(const LabelStmt *Node) {1468 OS << " '" << Node->getName() << "'";1469 if (Node->isSideEntry())1470 OS << " side_entry";1471}1472 1473void TextNodeDumper::VisitGotoStmt(const GotoStmt *Node) {1474 OS << " '" << Node->getLabel()->getName() << "'";1475 dumpPointer(Node->getLabel());1476}1477 1478void TextNodeDumper::VisitCaseStmt(const CaseStmt *Node) {1479 if (Node->caseStmtIsGNURange())1480 OS << " gnu_range";1481}1482 1483void clang::TextNodeDumper::VisitReturnStmt(const ReturnStmt *Node) {1484 if (const VarDecl *Cand = Node->getNRVOCandidate()) {1485 OS << " nrvo_candidate(";1486 dumpBareDeclRef(Cand);1487 OS << ")";1488 }1489}1490 1491void clang::TextNodeDumper::VisitCoawaitExpr(const CoawaitExpr *Node) {1492 if (Node->isImplicit())1493 OS << " implicit";1494}1495 1496void clang::TextNodeDumper::VisitCoreturnStmt(const CoreturnStmt *Node) {1497 if (Node->isImplicit())1498 OS << " implicit";1499}1500 1501void TextNodeDumper::VisitConstantExpr(const ConstantExpr *Node) {1502 if (Node->hasAPValueResult())1503 AddChild("value",1504 [=] { Visit(Node->getAPValueResult(), Node->getType()); });1505}1506 1507void TextNodeDumper::VisitCallExpr(const CallExpr *Node) {1508 if (Node->usesADL())1509 OS << " adl";1510 if (Node->hasStoredFPFeatures())1511 printFPOptions(Node->getFPFeatures());1512}1513 1514void TextNodeDumper::VisitCXXOperatorCallExpr(const CXXOperatorCallExpr *Node) {1515 const char *OperatorSpelling = clang::getOperatorSpelling(Node->getOperator());1516 if (OperatorSpelling)1517 OS << " '" << OperatorSpelling << "'";1518 1519 VisitCallExpr(Node);1520}1521 1522void TextNodeDumper::VisitCastExpr(const CastExpr *Node) {1523 OS << " <";1524 {1525 ColorScope Color(OS, ShowColors, CastColor);1526 OS << Node->getCastKindName();1527 }1528 dumpBasePath(OS, Node);1529 OS << ">";1530 if (Node->hasStoredFPFeatures())1531 printFPOptions(Node->getFPFeatures());1532}1533 1534void TextNodeDumper::VisitImplicitCastExpr(const ImplicitCastExpr *Node) {1535 VisitCastExpr(Node);1536 if (Node->isPartOfExplicitCast())1537 OS << " part_of_explicit_cast";1538}1539 1540void TextNodeDumper::VisitDeclRefExpr(const DeclRefExpr *Node) {1541 OS << " ";1542 dumpBareDeclRef(Node->getDecl());1543 dumpNestedNameSpecifier(Node->getQualifier());1544 if (Node->getDecl() != Node->getFoundDecl()) {1545 OS << " (";1546 dumpBareDeclRef(Node->getFoundDecl());1547 OS << ")";1548 }1549 switch (Node->isNonOdrUse()) {1550 case NOUR_None: break;1551 case NOUR_Unevaluated: OS << " non_odr_use_unevaluated"; break;1552 case NOUR_Constant: OS << " non_odr_use_constant"; break;1553 case NOUR_Discarded: OS << " non_odr_use_discarded"; break;1554 }1555 if (Node->isCapturedByCopyInLambdaWithExplicitObjectParameter())1556 OS << " dependent_capture";1557 else if (Node->refersToEnclosingVariableOrCapture())1558 OS << " refers_to_enclosing_variable_or_capture";1559 1560 if (Node->isImmediateEscalating())1561 OS << " immediate-escalating";1562}1563 1564void clang::TextNodeDumper::VisitDependentScopeDeclRefExpr(1565 const DependentScopeDeclRefExpr *Node) {1566 1567 dumpNestedNameSpecifier(Node->getQualifier());1568}1569 1570void TextNodeDumper::VisitUnresolvedLookupExpr(1571 const UnresolvedLookupExpr *Node) {1572 OS << " (";1573 if (!Node->requiresADL())1574 OS << "no ";1575 OS << "ADL) = '" << Node->getName() << '\'';1576 1577 UnresolvedLookupExpr::decls_iterator I = Node->decls_begin(),1578 E = Node->decls_end();1579 if (I == E)1580 OS << " empty";1581 for (; I != E; ++I)1582 dumpPointer(*I);1583}1584 1585void TextNodeDumper::VisitObjCIvarRefExpr(const ObjCIvarRefExpr *Node) {1586 {1587 ColorScope Color(OS, ShowColors, DeclKindNameColor);1588 OS << " " << Node->getDecl()->getDeclKindName() << "Decl";1589 }1590 OS << "='" << *Node->getDecl() << "'";1591 dumpPointer(Node->getDecl());1592 if (Node->isFreeIvar())1593 OS << " isFreeIvar";1594}1595 1596void TextNodeDumper::VisitSYCLUniqueStableNameExpr(1597 const SYCLUniqueStableNameExpr *Node) {1598 dumpType(Node->getTypeSourceInfo()->getType());1599}1600 1601void TextNodeDumper::VisitPredefinedExpr(const PredefinedExpr *Node) {1602 OS << " " << PredefinedExpr::getIdentKindName(Node->getIdentKind());1603}1604 1605void TextNodeDumper::VisitCharacterLiteral(const CharacterLiteral *Node) {1606 ColorScope Color(OS, ShowColors, ValueColor);1607 OS << " " << Node->getValue();1608}1609 1610void TextNodeDumper::VisitIntegerLiteral(const IntegerLiteral *Node) {1611 bool isSigned = Node->getType()->isSignedIntegerType();1612 ColorScope Color(OS, ShowColors, ValueColor);1613 OS << " " << toString(Node->getValue(), 10, isSigned);1614}1615 1616void TextNodeDumper::VisitFixedPointLiteral(const FixedPointLiteral *Node) {1617 ColorScope Color(OS, ShowColors, ValueColor);1618 OS << " " << Node->getValueAsString(/*Radix=*/10);1619}1620 1621void TextNodeDumper::VisitFloatingLiteral(const FloatingLiteral *Node) {1622 ColorScope Color(OS, ShowColors, ValueColor);1623 OS << " " << Node->getValueAsApproximateDouble();1624}1625 1626void TextNodeDumper::VisitStringLiteral(const StringLiteral *Str) {1627 ColorScope Color(OS, ShowColors, ValueColor);1628 OS << " ";1629 Str->outputString(OS);1630}1631 1632void TextNodeDumper::VisitInitListExpr(const InitListExpr *ILE) {1633 if (auto *Field = ILE->getInitializedFieldInUnion()) {1634 OS << " field ";1635 dumpBareDeclRef(Field);1636 }1637}1638 1639void TextNodeDumper::VisitGenericSelectionExpr(const GenericSelectionExpr *E) {1640 if (E->isResultDependent())1641 OS << " result_dependent";1642}1643 1644void TextNodeDumper::VisitUnaryOperator(const UnaryOperator *Node) {1645 OS << " " << (Node->isPostfix() ? "postfix" : "prefix") << " '"1646 << UnaryOperator::getOpcodeStr(Node->getOpcode()) << "'";1647 if (!Node->canOverflow())1648 OS << " cannot overflow";1649 if (Node->hasStoredFPFeatures())1650 printFPOptions(Node->getStoredFPFeatures());1651}1652 1653void TextNodeDumper::VisitUnaryExprOrTypeTraitExpr(1654 const UnaryExprOrTypeTraitExpr *Node) {1655 OS << " " << getTraitSpelling(Node->getKind());1656 1657 if (Node->isArgumentType())1658 dumpType(Node->getArgumentType());1659}1660 1661void TextNodeDumper::VisitMemberExpr(const MemberExpr *Node) {1662 OS << " " << (Node->isArrow() ? "->" : ".") << *Node->getMemberDecl();1663 dumpPointer(Node->getMemberDecl());1664 dumpNestedNameSpecifier(Node->getQualifier());1665 switch (Node->isNonOdrUse()) {1666 case NOUR_None: break;1667 case NOUR_Unevaluated: OS << " non_odr_use_unevaluated"; break;1668 case NOUR_Constant: OS << " non_odr_use_constant"; break;1669 case NOUR_Discarded: OS << " non_odr_use_discarded"; break;1670 }1671}1672 1673void TextNodeDumper::VisitExtVectorElementExpr(1674 const ExtVectorElementExpr *Node) {1675 OS << " " << Node->getAccessor().getNameStart();1676}1677 1678void TextNodeDumper::VisitBinaryOperator(const BinaryOperator *Node) {1679 OS << " '" << BinaryOperator::getOpcodeStr(Node->getOpcode()) << "'";1680 if (Node->hasStoredFPFeatures())1681 printFPOptions(Node->getStoredFPFeatures());1682}1683 1684void TextNodeDumper::VisitCompoundAssignOperator(1685 const CompoundAssignOperator *Node) {1686 OS << " '" << BinaryOperator::getOpcodeStr(Node->getOpcode())1687 << "' ComputeLHSTy=";1688 dumpBareType(Node->getComputationLHSType());1689 OS << " ComputeResultTy=";1690 dumpBareType(Node->getComputationResultType());1691 if (Node->hasStoredFPFeatures())1692 printFPOptions(Node->getStoredFPFeatures());1693}1694 1695void TextNodeDumper::VisitAddrLabelExpr(const AddrLabelExpr *Node) {1696 OS << " " << Node->getLabel()->getName();1697 dumpPointer(Node->getLabel());1698}1699 1700void TextNodeDumper::VisitCXXNamedCastExpr(const CXXNamedCastExpr *Node) {1701 OS << " " << Node->getCastName() << "<"1702 << Node->getTypeAsWritten().getAsString() << ">"1703 << " <" << Node->getCastKindName();1704 dumpBasePath(OS, Node);1705 OS << ">";1706}1707 1708void TextNodeDumper::VisitCXXBoolLiteralExpr(const CXXBoolLiteralExpr *Node) {1709 OS << " " << (Node->getValue() ? "true" : "false");1710}1711 1712void TextNodeDumper::VisitCXXThisExpr(const CXXThisExpr *Node) {1713 if (Node->isImplicit())1714 OS << " implicit";1715 if (Node->isCapturedByCopyInLambdaWithExplicitObjectParameter())1716 OS << " dependent_capture";1717 OS << " this";1718}1719 1720void TextNodeDumper::VisitCXXFunctionalCastExpr(1721 const CXXFunctionalCastExpr *Node) {1722 OS << " functional cast to " << Node->getTypeAsWritten().getAsString() << " <"1723 << Node->getCastKindName() << ">";1724 if (Node->hasStoredFPFeatures())1725 printFPOptions(Node->getFPFeatures());1726}1727 1728void TextNodeDumper::VisitCXXStaticCastExpr(const CXXStaticCastExpr *Node) {1729 VisitCXXNamedCastExpr(Node);1730 if (Node->hasStoredFPFeatures())1731 printFPOptions(Node->getFPFeatures());1732}1733 1734void TextNodeDumper::VisitCXXUnresolvedConstructExpr(1735 const CXXUnresolvedConstructExpr *Node) {1736 dumpType(Node->getTypeAsWritten());1737 if (Node->isListInitialization())1738 OS << " list";1739}1740 1741void TextNodeDumper::VisitCXXConstructExpr(const CXXConstructExpr *Node) {1742 CXXConstructorDecl *Ctor = Node->getConstructor();1743 dumpType(Ctor->getType());1744 if (Node->isElidable())1745 OS << " elidable";1746 if (Node->isListInitialization())1747 OS << " list";1748 if (Node->isStdInitListInitialization())1749 OS << " std::initializer_list";1750 if (Node->requiresZeroInitialization())1751 OS << " zeroing";1752 if (Node->isImmediateEscalating())1753 OS << " immediate-escalating";1754}1755 1756void TextNodeDumper::VisitCXXBindTemporaryExpr(1757 const CXXBindTemporaryExpr *Node) {1758 OS << " (CXXTemporary";1759 dumpPointer(Node);1760 OS << ")";1761}1762 1763void TextNodeDumper::VisitCXXNewExpr(const CXXNewExpr *Node) {1764 if (Node->isGlobalNew())1765 OS << " global";1766 if (Node->isArray())1767 OS << " array";1768 if (Node->getOperatorNew()) {1769 OS << ' ';1770 dumpBareDeclRef(Node->getOperatorNew());1771 }1772 // We could dump the deallocation function used in case of error, but it's1773 // usually not that interesting.1774}1775 1776void TextNodeDumper::VisitCXXDeleteExpr(const CXXDeleteExpr *Node) {1777 if (Node->isGlobalDelete())1778 OS << " global";1779 if (Node->isArrayForm())1780 OS << " array";1781 if (Node->getOperatorDelete()) {1782 OS << ' ';1783 dumpBareDeclRef(Node->getOperatorDelete());1784 }1785}1786 1787void TextNodeDumper::VisitTypeTraitExpr(const TypeTraitExpr *Node) {1788 OS << " " << getTraitSpelling(Node->getTrait());1789}1790 1791void TextNodeDumper::VisitArrayTypeTraitExpr(const ArrayTypeTraitExpr *Node) {1792 OS << " " << getTraitSpelling(Node->getTrait());1793}1794 1795void TextNodeDumper::VisitExpressionTraitExpr(const ExpressionTraitExpr *Node) {1796 OS << " " << getTraitSpelling(Node->getTrait());1797}1798 1799void TextNodeDumper::VisitCXXDefaultArgExpr(const CXXDefaultArgExpr *Node) {1800 if (Node->hasRewrittenInit())1801 OS << " has rewritten init";1802}1803 1804void TextNodeDumper::VisitCXXDefaultInitExpr(const CXXDefaultInitExpr *Node) {1805 if (Node->hasRewrittenInit())1806 OS << " has rewritten init";1807}1808 1809void TextNodeDumper::VisitMaterializeTemporaryExpr(1810 const MaterializeTemporaryExpr *Node) {1811 if (const ValueDecl *VD = Node->getExtendingDecl()) {1812 OS << " extended by ";1813 dumpBareDeclRef(VD);1814 }1815}1816 1817void TextNodeDumper::VisitExprWithCleanups(const ExprWithCleanups *Node) {1818 for (unsigned i = 0, e = Node->getNumObjects(); i != e; ++i)1819 dumpCleanupObject(Node->getObject(i));1820}1821 1822void TextNodeDumper::VisitSizeOfPackExpr(const SizeOfPackExpr *Node) {1823 dumpPointer(Node->getPack());1824 dumpName(Node->getPack());1825}1826 1827void TextNodeDumper::VisitCXXDependentScopeMemberExpr(1828 const CXXDependentScopeMemberExpr *Node) {1829 OS << " " << (Node->isArrow() ? "->" : ".") << Node->getMember();1830}1831 1832void TextNodeDumper::VisitObjCMessageExpr(const ObjCMessageExpr *Node) {1833 OS << " selector=";1834 Node->getSelector().print(OS);1835 switch (Node->getReceiverKind()) {1836 case ObjCMessageExpr::Instance:1837 break;1838 1839 case ObjCMessageExpr::Class:1840 OS << " class=";1841 dumpBareType(Node->getClassReceiver());1842 break;1843 1844 case ObjCMessageExpr::SuperInstance:1845 OS << " super (instance)";1846 break;1847 1848 case ObjCMessageExpr::SuperClass:1849 OS << " super (class)";1850 break;1851 }1852}1853 1854void TextNodeDumper::VisitObjCBoxedExpr(const ObjCBoxedExpr *Node) {1855 if (auto *BoxingMethod = Node->getBoxingMethod()) {1856 OS << " selector=";1857 BoxingMethod->getSelector().print(OS);1858 }1859}1860 1861void TextNodeDumper::VisitObjCAtCatchStmt(const ObjCAtCatchStmt *Node) {1862 if (!Node->getCatchParamDecl())1863 OS << " catch all";1864}1865 1866void TextNodeDumper::VisitObjCEncodeExpr(const ObjCEncodeExpr *Node) {1867 dumpType(Node->getEncodedType());1868}1869 1870void TextNodeDumper::VisitObjCSelectorExpr(const ObjCSelectorExpr *Node) {1871 OS << " ";1872 Node->getSelector().print(OS);1873}1874 1875void TextNodeDumper::VisitObjCProtocolExpr(const ObjCProtocolExpr *Node) {1876 OS << ' ' << *Node->getProtocol();1877}1878 1879void TextNodeDumper::VisitObjCPropertyRefExpr(const ObjCPropertyRefExpr *Node) {1880 if (Node->isImplicitProperty()) {1881 OS << " Kind=MethodRef Getter=\"";1882 if (Node->getImplicitPropertyGetter())1883 Node->getImplicitPropertyGetter()->getSelector().print(OS);1884 else1885 OS << "(null)";1886 1887 OS << "\" Setter=\"";1888 if (ObjCMethodDecl *Setter = Node->getImplicitPropertySetter())1889 Setter->getSelector().print(OS);1890 else1891 OS << "(null)";1892 OS << "\"";1893 } else {1894 OS << " Kind=PropertyRef Property=\"" << *Node->getExplicitProperty()1895 << '"';1896 }1897 1898 if (Node->isSuperReceiver())1899 OS << " super";1900 1901 OS << " Messaging=";1902 if (Node->isMessagingGetter() && Node->isMessagingSetter())1903 OS << "Getter&Setter";1904 else if (Node->isMessagingGetter())1905 OS << "Getter";1906 else if (Node->isMessagingSetter())1907 OS << "Setter";1908}1909 1910void TextNodeDumper::VisitObjCSubscriptRefExpr(1911 const ObjCSubscriptRefExpr *Node) {1912 if (Node->isArraySubscriptRefExpr())1913 OS << " Kind=ArraySubscript GetterForArray=\"";1914 else1915 OS << " Kind=DictionarySubscript GetterForDictionary=\"";1916 if (Node->getAtIndexMethodDecl())1917 Node->getAtIndexMethodDecl()->getSelector().print(OS);1918 else1919 OS << "(null)";1920 1921 if (Node->isArraySubscriptRefExpr())1922 OS << "\" SetterForArray=\"";1923 else1924 OS << "\" SetterForDictionary=\"";1925 if (Node->setAtIndexMethodDecl())1926 Node->setAtIndexMethodDecl()->getSelector().print(OS);1927 else1928 OS << "(null)";1929}1930 1931void TextNodeDumper::VisitObjCBoolLiteralExpr(const ObjCBoolLiteralExpr *Node) {1932 OS << " " << (Node->getValue() ? "__objc_yes" : "__objc_no");1933}1934 1935void TextNodeDumper::VisitOMPIteratorExpr(const OMPIteratorExpr *Node) {1936 OS << " ";1937 for (unsigned I = 0, E = Node->numOfIterators(); I < E; ++I) {1938 Visit(Node->getIteratorDecl(I));1939 OS << " = ";1940 const OMPIteratorExpr::IteratorRange Range = Node->getIteratorRange(I);1941 OS << " begin ";1942 Visit(Range.Begin);1943 OS << " end ";1944 Visit(Range.End);1945 if (Range.Step) {1946 OS << " step ";1947 Visit(Range.Step);1948 }1949 }1950}1951 1952void TextNodeDumper::VisitConceptSpecializationExpr(1953 const ConceptSpecializationExpr *Node) {1954 OS << " ";1955 dumpBareDeclRef(Node->getFoundDecl());1956}1957 1958void TextNodeDumper::VisitRequiresExpr(1959 const RequiresExpr *Node) {1960 if (!Node->isValueDependent())1961 OS << (Node->isSatisfied() ? " satisfied" : " unsatisfied");1962}1963 1964void TextNodeDumper::VisitRValueReferenceType(const ReferenceType *T) {1965 if (T->isSpelledAsLValue())1966 OS << " written as lvalue reference";1967}1968 1969void TextNodeDumper::VisitArrayType(const ArrayType *T) {1970 switch (T->getSizeModifier()) {1971 case ArraySizeModifier::Normal:1972 break;1973 case ArraySizeModifier::Static:1974 OS << " static";1975 break;1976 case ArraySizeModifier::Star:1977 OS << " *";1978 break;1979 }1980 OS << " " << T->getIndexTypeQualifiers().getAsString();1981}1982 1983void TextNodeDumper::VisitConstantArrayType(const ConstantArrayType *T) {1984 OS << " " << T->getSize();1985 VisitArrayType(T);1986}1987 1988void TextNodeDumper::VisitVariableArrayType(const VariableArrayType *T) {1989 VisitArrayType(T);1990}1991 1992void TextNodeDumper::VisitDependentSizedArrayType(1993 const DependentSizedArrayType *T) {1994 VisitArrayType(T);1995}1996 1997void TextNodeDumper::VisitDependentSizedExtVectorType(1998 const DependentSizedExtVectorType *T) {1999 OS << " ";2000 dumpLocation(T->getAttributeLoc());2001}2002 2003void TextNodeDumper::VisitVectorType(const VectorType *T) {2004 switch (T->getVectorKind()) {2005 case VectorKind::Generic:2006 break;2007 case VectorKind::AltiVecVector:2008 OS << " altivec";2009 break;2010 case VectorKind::AltiVecPixel:2011 OS << " altivec pixel";2012 break;2013 case VectorKind::AltiVecBool:2014 OS << " altivec bool";2015 break;2016 case VectorKind::Neon:2017 OS << " neon";2018 break;2019 case VectorKind::NeonPoly:2020 OS << " neon poly";2021 break;2022 case VectorKind::SveFixedLengthData:2023 OS << " fixed-length sve data vector";2024 break;2025 case VectorKind::SveFixedLengthPredicate:2026 OS << " fixed-length sve predicate vector";2027 break;2028 case VectorKind::RVVFixedLengthData:2029 OS << " fixed-length rvv data vector";2030 break;2031 case VectorKind::RVVFixedLengthMask:2032 case VectorKind::RVVFixedLengthMask_1:2033 case VectorKind::RVVFixedLengthMask_2:2034 case VectorKind::RVVFixedLengthMask_4:2035 OS << " fixed-length rvv mask vector";2036 break;2037 }2038 OS << " " << T->getNumElements();2039}2040 2041void TextNodeDumper::VisitFunctionType(const FunctionType *T) {2042 auto EI = T->getExtInfo();2043 if (EI.getNoReturn())2044 OS << " noreturn";2045 if (EI.getProducesResult())2046 OS << " produces_result";2047 if (EI.getHasRegParm())2048 OS << " regparm " << EI.getRegParm();2049 OS << " " << FunctionType::getNameForCallConv(EI.getCC());2050}2051 2052void TextNodeDumper::VisitFunctionProtoType(const FunctionProtoType *T) {2053 auto EPI = T->getExtProtoInfo();2054 if (EPI.HasTrailingReturn)2055 OS << " trailing_return";2056 if (T->isConst())2057 OS << " const";2058 if (T->isVolatile())2059 OS << " volatile";2060 if (T->isRestrict())2061 OS << " restrict";2062 if (T->getExtProtoInfo().Variadic)2063 OS << " variadic";2064 switch (EPI.RefQualifier) {2065 case RQ_None:2066 break;2067 case RQ_LValue:2068 OS << " &";2069 break;2070 case RQ_RValue:2071 OS << " &&";2072 break;2073 }2074 2075 switch (EPI.ExceptionSpec.Type) {2076 case EST_None:2077 break;2078 case EST_DynamicNone:2079 OS << " exceptionspec_dynamic_none";2080 break;2081 case EST_Dynamic:2082 OS << " exceptionspec_dynamic";2083 break;2084 case EST_MSAny:2085 OS << " exceptionspec_ms_any";2086 break;2087 case EST_NoThrow:2088 OS << " exceptionspec_nothrow";2089 break;2090 case EST_BasicNoexcept:2091 OS << " exceptionspec_basic_noexcept";2092 break;2093 case EST_DependentNoexcept:2094 OS << " exceptionspec_dependent_noexcept";2095 break;2096 case EST_NoexceptFalse:2097 OS << " exceptionspec_noexcept_false";2098 break;2099 case EST_NoexceptTrue:2100 OS << " exceptionspec_noexcept_true";2101 break;2102 case EST_Unevaluated:2103 OS << " exceptionspec_unevaluated";2104 break;2105 case EST_Uninstantiated:2106 OS << " exceptionspec_uninstantiated";2107 break;2108 case EST_Unparsed:2109 OS << " exceptionspec_unparsed";2110 break;2111 }2112 if (!EPI.ExceptionSpec.Exceptions.empty()) {2113 AddChild([=] {2114 OS << "Exceptions:";2115 for (unsigned I = 0, N = EPI.ExceptionSpec.Exceptions.size(); I != N;2116 ++I) {2117 if (I)2118 OS << ",";2119 dumpType(EPI.ExceptionSpec.Exceptions[I]);2120 }2121 });2122 }2123 if (EPI.ExceptionSpec.NoexceptExpr) {2124 AddChild([=] {2125 OS << "NoexceptExpr: ";2126 Visit(EPI.ExceptionSpec.NoexceptExpr);2127 });2128 }2129 dumpDeclRef(EPI.ExceptionSpec.SourceDecl, "ExceptionSourceDecl");2130 dumpDeclRef(EPI.ExceptionSpec.SourceTemplate, "ExceptionSourceTemplate");2131 2132 // FIXME: Consumed parameters.2133 VisitFunctionType(T);2134}2135 2136void TextNodeDumper::VisitUnresolvedUsingType(const UnresolvedUsingType *T) {2137 if (ElaboratedTypeKeyword K = T->getKeyword();2138 K != ElaboratedTypeKeyword::None)2139 OS << ' ' << TypeWithKeyword::getKeywordName(K);2140 dumpNestedNameSpecifier(T->getQualifier());2141 dumpDeclRef(T->getDecl());2142}2143 2144void TextNodeDumper::VisitUsingType(const UsingType *T) {2145 if (ElaboratedTypeKeyword K = T->getKeyword();2146 K != ElaboratedTypeKeyword::None)2147 OS << ' ' << TypeWithKeyword::getKeywordName(K);2148 dumpNestedNameSpecifier(T->getQualifier());2149 dumpDeclRef(T->getDecl());2150 dumpType(T->desugar());2151}2152 2153void TextNodeDumper::VisitTypedefType(const TypedefType *T) {2154 if (ElaboratedTypeKeyword K = T->getKeyword();2155 K != ElaboratedTypeKeyword::None)2156 OS << ' ' << TypeWithKeyword::getKeywordName(K);2157 dumpNestedNameSpecifier(T->getQualifier());2158 dumpDeclRef(T->getDecl());2159 if (!T->typeMatchesDecl()) {2160 OS << " divergent";2161 dumpType(T->desugar());2162 }2163}2164 2165void TextNodeDumper::VisitUnaryTransformType(const UnaryTransformType *T) {2166 switch (T->getUTTKind()) {2167#define TRANSFORM_TYPE_TRAIT_DEF(Enum, Trait) \2168 case UnaryTransformType::Enum: \2169 OS << " " #Trait; \2170 break;2171#include "clang/Basic/TransformTypeTraits.def"2172 }2173}2174 2175void TextNodeDumper::VisitTagType(const TagType *T) {2176 if (T->isCanonicalUnqualified())2177 OS << " canonical";2178 if (T->isTagOwned())2179 OS << " owns_tag";2180 if (T->isInjected())2181 OS << " injected";2182 if (ElaboratedTypeKeyword K = T->getKeyword();2183 K != ElaboratedTypeKeyword::None)2184 OS << ' ' << TypeWithKeyword::getKeywordName(K);2185 dumpNestedNameSpecifier(T->getQualifier());2186 dumpDeclRef(T->getDecl());2187}2188 2189void TextNodeDumper::VisitTemplateTypeParmType(const TemplateTypeParmType *T) {2190 OS << " depth " << T->getDepth() << " index " << T->getIndex();2191 if (T->isParameterPack())2192 OS << " pack";2193 dumpDeclRef(T->getDecl());2194}2195 2196void TextNodeDumper::VisitSubstTemplateTypeParmType(2197 const SubstTemplateTypeParmType *T) {2198 dumpDeclRef(T->getAssociatedDecl());2199 VisitTemplateTypeParmDecl(T->getReplacedParameter());2200 if (auto PackIndex = T->getPackIndex())2201 OS << " pack_index " << *PackIndex;2202 if (T->getFinal())2203 OS << " final";2204}2205 2206void TextNodeDumper::VisitSubstTemplateTypeParmPackType(2207 const SubstTemplateTypeParmPackType *T) {2208 dumpDeclRef(T->getAssociatedDecl());2209 VisitTemplateTypeParmDecl(T->getReplacedParameter());2210}2211 2212void TextNodeDumper::VisitAutoType(const AutoType *T) {2213 if (T->isDecltypeAuto())2214 OS << " decltype(auto)";2215 if (!T->isDeduced())2216 OS << " undeduced";2217 if (T->isConstrained())2218 dumpDeclRef(T->getTypeConstraintConcept());2219}2220 2221void TextNodeDumper::VisitDeducedTemplateSpecializationType(2222 const DeducedTemplateSpecializationType *T) {2223 dumpTemplateName(T->getTemplateName(), "name");2224}2225 2226void TextNodeDumper::VisitTemplateSpecializationType(2227 const TemplateSpecializationType *T) {2228 if (T->isTypeAlias())2229 OS << " alias";2230 if (ElaboratedTypeKeyword K = T->getKeyword();2231 K != ElaboratedTypeKeyword::None)2232 OS << ' ' << TypeWithKeyword::getKeywordName(K);2233 dumpTemplateName(T->getTemplateName(), "name");2234}2235 2236void TextNodeDumper::VisitInjectedClassNameType(2237 const InjectedClassNameType *T) {2238 dumpDeclRef(T->getDecl());2239}2240 2241void TextNodeDumper::VisitObjCInterfaceType(const ObjCInterfaceType *T) {2242 dumpDeclRef(T->getDecl());2243}2244 2245void TextNodeDumper::VisitPackExpansionType(const PackExpansionType *T) {2246 if (auto N = T->getNumExpansions())2247 OS << " expansions " << *N;2248}2249 2250void TextNodeDumper::VisitTypeLoc(TypeLoc TL) {2251 // By default, add extra Type details with no extra loc info.2252 TypeVisitor<TextNodeDumper>::Visit(TL.getTypePtr());2253}2254// FIXME: override behavior for TypeLocs that have interesting location2255// information, such as the qualifier in ElaboratedTypeLoc.2256 2257void TextNodeDumper::VisitLabelDecl(const LabelDecl *D) { dumpName(D); }2258 2259void TextNodeDumper::VisitTypedefDecl(const TypedefDecl *D) {2260 dumpName(D);2261 dumpType(D->getUnderlyingType());2262 if (D->isModulePrivate())2263 OS << " __module_private__";2264}2265 2266void TextNodeDumper::VisitEnumDecl(const EnumDecl *D) {2267 if (D->isScoped()) {2268 if (D->isScopedUsingClassTag())2269 OS << " class";2270 else2271 OS << " struct";2272 }2273 dumpName(D);2274 if (D->isModulePrivate())2275 OS << " __module_private__";2276 if (D->isFixed())2277 dumpType(D->getIntegerType());2278 2279 if (const auto *Instance = D->getTemplateInstantiationPattern()) {2280 OS << " instantiated_from";2281 dumpPointer(Instance);2282 }2283}2284 2285void TextNodeDumper::VisitRecordDecl(const RecordDecl *D) {2286 OS << ' ' << D->getKindName();2287 dumpName(D);2288 if (D->isModulePrivate())2289 OS << " __module_private__";2290 if (D->isCompleteDefinition())2291 OS << " definition";2292}2293 2294void TextNodeDumper::VisitEnumConstantDecl(const EnumConstantDecl *D) {2295 dumpName(D);2296 dumpType(D->getType());2297}2298 2299void TextNodeDumper::VisitIndirectFieldDecl(const IndirectFieldDecl *D) {2300 dumpName(D);2301 dumpType(D->getType());2302 2303 for (const auto *Child : D->chain())2304 dumpDeclRef(Child);2305}2306 2307void TextNodeDumper::VisitFunctionDecl(const FunctionDecl *D) {2308 dumpName(D);2309 dumpType(D->getType());2310 dumpTemplateSpecializationKind(D->getTemplateSpecializationKind());2311 2312 StorageClass SC = D->getStorageClass();2313 if (SC != SC_None)2314 OS << ' ' << VarDecl::getStorageClassSpecifierString(SC);2315 if (D->isInlineSpecified())2316 OS << " inline";2317 if (D->isVirtualAsWritten())2318 OS << " virtual";2319 if (D->isModulePrivate())2320 OS << " __module_private__";2321 2322 if (D->isPureVirtual())2323 OS << " pure";2324 if (D->isDefaulted()) {2325 OS << " default";2326 if (D->isDeleted())2327 OS << "_delete";2328 }2329 if (D->isDeletedAsWritten())2330 OS << " delete";2331 if (D->isTrivial())2332 OS << " trivial";2333 2334 if (const StringLiteral *M = D->getDeletedMessage())2335 AddChild("delete message", [=] { Visit(M); });2336 2337 if (D->isIneligibleOrNotSelected())2338 OS << (isa<CXXDestructorDecl>(D) ? " not_selected" : " ineligible");2339 2340 if (const auto *FPT = D->getType()->getAs<FunctionProtoType>()) {2341 FunctionProtoType::ExtProtoInfo EPI = FPT->getExtProtoInfo();2342 switch (EPI.ExceptionSpec.Type) {2343 default:2344 break;2345 case EST_Unevaluated:2346 OS << " noexcept-unevaluated " << EPI.ExceptionSpec.SourceDecl;2347 break;2348 case EST_Uninstantiated:2349 OS << " noexcept-uninstantiated " << EPI.ExceptionSpec.SourceTemplate;2350 break;2351 }2352 }2353 2354 if (const auto *MD = dyn_cast<CXXMethodDecl>(D)) {2355 if (MD->size_overridden_methods() != 0) {2356 auto dumpOverride = [=](const CXXMethodDecl *D) {2357 SplitQualType T_split = D->getType().split();2358 OS << D << " " << D->getParent()->getName() << "::" << D->getDeclName()2359 << " '" << QualType::getAsString(T_split, PrintPolicy) << "'";2360 };2361 2362 AddChild([=] {2363 auto Overrides = MD->overridden_methods();2364 OS << "Overrides: [ ";2365 dumpOverride(*Overrides.begin());2366 for (const auto *Override : llvm::drop_begin(Overrides)) {2367 OS << ", ";2368 dumpOverride(Override);2369 }2370 OS << " ]";2371 });2372 }2373 }2374 2375 if (!D->isInlineSpecified() && D->isInlined()) {2376 OS << " implicit-inline";2377 }2378 // Since NumParams comes from the FunctionProtoType of the FunctionDecl and2379 // the Params are set later, it is possible for a dump during debugging to2380 // encounter a FunctionDecl that has been created but hasn't been assigned2381 // ParmVarDecls yet.2382 if (!D->param_empty() && !D->param_begin())2383 OS << " <<<NULL params x " << D->getNumParams() << ">>>";2384 2385 if (const auto *Instance = D->getTemplateInstantiationPattern()) {2386 OS << " instantiated_from";2387 dumpPointer(Instance);2388 }2389}2390 2391void TextNodeDumper::VisitCXXDeductionGuideDecl(2392 const CXXDeductionGuideDecl *D) {2393 VisitFunctionDecl(D);2394 switch (D->getDeductionCandidateKind()) {2395 case DeductionCandidate::Normal:2396 case DeductionCandidate::Copy:2397 return;2398 case DeductionCandidate::Aggregate:2399 OS << " aggregate ";2400 break;2401 }2402}2403 2404void TextNodeDumper::VisitLifetimeExtendedTemporaryDecl(2405 const LifetimeExtendedTemporaryDecl *D) {2406 OS << " extended by ";2407 dumpBareDeclRef(D->getExtendingDecl());2408 OS << " mangling ";2409 {2410 ColorScope Color(OS, ShowColors, ValueColor);2411 OS << D->getManglingNumber();2412 }2413}2414 2415void TextNodeDumper::VisitFieldDecl(const FieldDecl *D) {2416 dumpName(D);2417 dumpType(D->getType());2418 if (D->isMutable())2419 OS << " mutable";2420 if (D->isModulePrivate())2421 OS << " __module_private__";2422}2423 2424void TextNodeDumper::VisitVarDecl(const VarDecl *D) {2425 dumpNestedNameSpecifier(D->getQualifier());2426 dumpName(D);2427 if (const auto *P = dyn_cast<ParmVarDecl>(D);2428 P && P->isExplicitObjectParameter())2429 OS << " this";2430 2431 dumpType(D->getType());2432 dumpTemplateSpecializationKind(D->getTemplateSpecializationKind());2433 StorageClass SC = D->getStorageClass();2434 if (SC != SC_None)2435 OS << ' ' << VarDecl::getStorageClassSpecifierString(SC);2436 switch (D->getTLSKind()) {2437 case VarDecl::TLS_None:2438 break;2439 case VarDecl::TLS_Static:2440 OS << " tls";2441 break;2442 case VarDecl::TLS_Dynamic:2443 OS << " tls_dynamic";2444 break;2445 }2446 if (D->isModulePrivate())2447 OS << " __module_private__";2448 if (D->isNRVOVariable())2449 OS << " nrvo";2450 if (D->isInline())2451 OS << " inline";2452 if (D->isConstexpr())2453 OS << " constexpr";2454 if (D->hasInit()) {2455 switch (D->getInitStyle()) {2456 case VarDecl::CInit:2457 OS << " cinit";2458 break;2459 case VarDecl::CallInit:2460 OS << " callinit";2461 break;2462 case VarDecl::ListInit:2463 OS << " listinit";2464 break;2465 case VarDecl::ParenListInit:2466 OS << " parenlistinit";2467 }2468 }2469 if (D->needsDestruction(D->getASTContext()))2470 OS << " destroyed";2471 if (D->isParameterPack())2472 OS << " pack";2473 2474 if (const auto *Instance = D->getTemplateInstantiationPattern()) {2475 OS << " instantiated_from";2476 dumpPointer(Instance);2477 }2478 2479 if (D->hasInit()) {2480 const Expr *E = D->getInit();2481 // Only dump the value of constexpr VarDecls for now.2482 if (E && !E->isValueDependent() && D->isConstexpr() &&2483 !D->getType()->isDependentType()) {2484 const APValue *Value = D->evaluateValue();2485 if (Value)2486 AddChild("value", [=] { Visit(*Value, E->getType()); });2487 }2488 }2489}2490 2491void TextNodeDumper::VisitBindingDecl(const BindingDecl *D) {2492 dumpName(D);2493 dumpType(D->getType());2494}2495 2496void TextNodeDumper::VisitCapturedDecl(const CapturedDecl *D) {2497 if (D->isNothrow())2498 OS << " nothrow";2499}2500 2501void TextNodeDumper::VisitImportDecl(const ImportDecl *D) {2502 OS << ' ' << D->getImportedModule()->getFullModuleName();2503 2504 for (Decl *InitD :2505 D->getASTContext().getModuleInitializers(D->getImportedModule()))2506 dumpDeclRef(InitD, "initializer");2507}2508 2509void TextNodeDumper::VisitPragmaCommentDecl(const PragmaCommentDecl *D) {2510 OS << ' ';2511 switch (D->getCommentKind()) {2512 case PCK_Unknown:2513 llvm_unreachable("unexpected pragma comment kind");2514 case PCK_Compiler:2515 OS << "compiler";2516 break;2517 case PCK_ExeStr:2518 OS << "exestr";2519 break;2520 case PCK_Lib:2521 OS << "lib";2522 break;2523 case PCK_Linker:2524 OS << "linker";2525 break;2526 case PCK_User:2527 OS << "user";2528 break;2529 }2530 StringRef Arg = D->getArg();2531 if (!Arg.empty())2532 OS << " \"" << Arg << "\"";2533}2534 2535void TextNodeDumper::VisitPragmaDetectMismatchDecl(2536 const PragmaDetectMismatchDecl *D) {2537 OS << " \"" << D->getName() << "\" \"" << D->getValue() << "\"";2538}2539 2540void TextNodeDumper::VisitOMPExecutableDirective(2541 const OMPExecutableDirective *D) {2542 if (D->isStandaloneDirective())2543 OS << " openmp_standalone_directive";2544}2545 2546void TextNodeDumper::VisitOMPDeclareReductionDecl(2547 const OMPDeclareReductionDecl *D) {2548 dumpName(D);2549 dumpType(D->getType());2550 OS << " combiner";2551 dumpPointer(D->getCombiner());2552 if (const auto *Initializer = D->getInitializer()) {2553 OS << " initializer";2554 dumpPointer(Initializer);2555 switch (D->getInitializerKind()) {2556 case OMPDeclareReductionInitKind::Direct:2557 OS << " omp_priv = ";2558 break;2559 case OMPDeclareReductionInitKind::Copy:2560 OS << " omp_priv ()";2561 break;2562 case OMPDeclareReductionInitKind::Call:2563 break;2564 }2565 }2566}2567 2568void TextNodeDumper::VisitOMPRequiresDecl(const OMPRequiresDecl *D) {2569 for (const auto *C : D->clauselists()) {2570 AddChild([=] {2571 if (!C) {2572 ColorScope Color(OS, ShowColors, NullColor);2573 OS << "<<<NULL>>> OMPClause";2574 return;2575 }2576 {2577 ColorScope Color(OS, ShowColors, AttrColor);2578 StringRef ClauseName(2579 llvm::omp::getOpenMPClauseName(C->getClauseKind()));2580 OS << "OMP" << ClauseName.substr(/*Start=*/0, /*N=*/1).upper()2581 << ClauseName.drop_front() << "Clause";2582 }2583 dumpPointer(C);2584 dumpSourceRange(SourceRange(C->getBeginLoc(), C->getEndLoc()));2585 });2586 }2587}2588 2589void TextNodeDumper::VisitOMPCapturedExprDecl(const OMPCapturedExprDecl *D) {2590 dumpName(D);2591 dumpType(D->getType());2592}2593 2594void TextNodeDumper::VisitNamespaceDecl(const NamespaceDecl *D) {2595 dumpName(D);2596 if (D->isInline())2597 OS << " inline";2598 if (D->isNested())2599 OS << " nested";2600 if (!D->isFirstDecl())2601 dumpDeclRef(D->getFirstDecl(), "original");2602}2603 2604void TextNodeDumper::VisitUsingDirectiveDecl(const UsingDirectiveDecl *D) {2605 OS << ' ';2606 dumpBareDeclRef(D->getNominatedNamespace());2607}2608 2609void TextNodeDumper::VisitNamespaceAliasDecl(const NamespaceAliasDecl *D) {2610 dumpName(D);2611 dumpDeclRef(D->getAliasedNamespace());2612}2613 2614void TextNodeDumper::VisitTypeAliasDecl(const TypeAliasDecl *D) {2615 dumpName(D);2616 dumpType(D->getUnderlyingType());2617}2618 2619void TextNodeDumper::VisitTypeAliasTemplateDecl(2620 const TypeAliasTemplateDecl *D) {2621 dumpName(D);2622}2623 2624void TextNodeDumper::VisitCXXRecordDecl(const CXXRecordDecl *D) {2625 VisitRecordDecl(D);2626 if (const auto *Instance = D->getTemplateInstantiationPattern()) {2627 OS << " instantiated_from";2628 dumpPointer(Instance);2629 }2630 if (const auto *CTSD = dyn_cast<ClassTemplateSpecializationDecl>(D)) {2631 dumpTemplateSpecializationKind(CTSD->getSpecializationKind());2632 if (CTSD->hasStrictPackMatch())2633 OS << " strict-pack-match";2634 }2635 2636 dumpNestedNameSpecifier(D->getQualifier());2637 2638 if (!D->isCompleteDefinition())2639 return;2640 2641 AddChild([=] {2642 {2643 ColorScope Color(OS, ShowColors, DeclKindNameColor);2644 OS << "DefinitionData";2645 }2646#define FLAG(fn, name) \2647 if (D->fn()) \2648 OS << " " #name;2649 FLAG(isParsingBaseSpecifiers, parsing_base_specifiers);2650 2651 FLAG(isGenericLambda, generic);2652 FLAG(isLambda, lambda);2653 2654 FLAG(isAnonymousStructOrUnion, is_anonymous);2655 FLAG(canPassInRegisters, pass_in_registers);2656 FLAG(isEmpty, empty);2657 FLAG(isAggregate, aggregate);2658 FLAG(isStandardLayout, standard_layout);2659 FLAG(isTriviallyCopyable, trivially_copyable);2660 FLAG(isPOD, pod);2661 FLAG(isTrivial, trivial);2662 FLAG(isPolymorphic, polymorphic);2663 FLAG(isAbstract, abstract);2664 FLAG(isLiteral, literal);2665 2666 FLAG(hasUserDeclaredConstructor, has_user_declared_ctor);2667 FLAG(hasConstexprNonCopyMoveConstructor, has_constexpr_non_copy_move_ctor);2668 FLAG(hasMutableFields, has_mutable_fields);2669 FLAG(hasVariantMembers, has_variant_members);2670 FLAG(allowConstDefaultInit, can_const_default_init);2671 2672 AddChild([=] {2673 {2674 ColorScope Color(OS, ShowColors, DeclKindNameColor);2675 OS << "DefaultConstructor";2676 }2677 FLAG(hasDefaultConstructor, exists);2678 FLAG(hasTrivialDefaultConstructor, trivial);2679 FLAG(hasNonTrivialDefaultConstructor, non_trivial);2680 FLAG(hasUserProvidedDefaultConstructor, user_provided);2681 FLAG(hasConstexprDefaultConstructor, constexpr);2682 FLAG(needsImplicitDefaultConstructor, needs_implicit);2683 FLAG(defaultedDefaultConstructorIsConstexpr, defaulted_is_constexpr);2684 });2685 2686 AddChild([=] {2687 {2688 ColorScope Color(OS, ShowColors, DeclKindNameColor);2689 OS << "CopyConstructor";2690 }2691 FLAG(hasSimpleCopyConstructor, simple);2692 FLAG(hasTrivialCopyConstructor, trivial);2693 FLAG(hasNonTrivialCopyConstructor, non_trivial);2694 FLAG(hasUserDeclaredCopyConstructor, user_declared);2695 FLAG(hasCopyConstructorWithConstParam, has_const_param);2696 FLAG(needsImplicitCopyConstructor, needs_implicit);2697 FLAG(needsOverloadResolutionForCopyConstructor,2698 needs_overload_resolution);2699 if (!D->needsOverloadResolutionForCopyConstructor())2700 FLAG(defaultedCopyConstructorIsDeleted, defaulted_is_deleted);2701 FLAG(implicitCopyConstructorHasConstParam, implicit_has_const_param);2702 });2703 2704 AddChild([=] {2705 {2706 ColorScope Color(OS, ShowColors, DeclKindNameColor);2707 OS << "MoveConstructor";2708 }2709 FLAG(hasMoveConstructor, exists);2710 FLAG(hasSimpleMoveConstructor, simple);2711 FLAG(hasTrivialMoveConstructor, trivial);2712 FLAG(hasNonTrivialMoveConstructor, non_trivial);2713 FLAG(hasUserDeclaredMoveConstructor, user_declared);2714 FLAG(needsImplicitMoveConstructor, needs_implicit);2715 FLAG(needsOverloadResolutionForMoveConstructor,2716 needs_overload_resolution);2717 if (!D->needsOverloadResolutionForMoveConstructor())2718 FLAG(defaultedMoveConstructorIsDeleted, defaulted_is_deleted);2719 });2720 2721 AddChild([=] {2722 {2723 ColorScope Color(OS, ShowColors, DeclKindNameColor);2724 OS << "CopyAssignment";2725 }2726 FLAG(hasSimpleCopyAssignment, simple);2727 FLAG(hasTrivialCopyAssignment, trivial);2728 FLAG(hasNonTrivialCopyAssignment, non_trivial);2729 FLAG(hasCopyAssignmentWithConstParam, has_const_param);2730 FLAG(hasUserDeclaredCopyAssignment, user_declared);2731 FLAG(needsImplicitCopyAssignment, needs_implicit);2732 FLAG(needsOverloadResolutionForCopyAssignment, needs_overload_resolution);2733 FLAG(implicitCopyAssignmentHasConstParam, implicit_has_const_param);2734 });2735 2736 AddChild([=] {2737 {2738 ColorScope Color(OS, ShowColors, DeclKindNameColor);2739 OS << "MoveAssignment";2740 }2741 FLAG(hasMoveAssignment, exists);2742 FLAG(hasSimpleMoveAssignment, simple);2743 FLAG(hasTrivialMoveAssignment, trivial);2744 FLAG(hasNonTrivialMoveAssignment, non_trivial);2745 FLAG(hasUserDeclaredMoveAssignment, user_declared);2746 FLAG(needsImplicitMoveAssignment, needs_implicit);2747 FLAG(needsOverloadResolutionForMoveAssignment, needs_overload_resolution);2748 });2749 2750 AddChild([=] {2751 {2752 ColorScope Color(OS, ShowColors, DeclKindNameColor);2753 OS << "Destructor";2754 }2755 FLAG(hasSimpleDestructor, simple);2756 FLAG(hasIrrelevantDestructor, irrelevant);2757 FLAG(hasTrivialDestructor, trivial);2758 FLAG(hasNonTrivialDestructor, non_trivial);2759 FLAG(hasUserDeclaredDestructor, user_declared);2760 FLAG(hasConstexprDestructor, constexpr);2761 FLAG(needsImplicitDestructor, needs_implicit);2762 FLAG(needsOverloadResolutionForDestructor, needs_overload_resolution);2763 if (!D->needsOverloadResolutionForDestructor())2764 FLAG(defaultedDestructorIsDeleted, defaulted_is_deleted);2765 });2766 });2767 2768 for (const auto &I : D->bases()) {2769 AddChild([=] {2770 if (I.isVirtual())2771 OS << "virtual ";2772 dumpAccessSpecifier(I.getAccessSpecifier());2773 dumpType(I.getType());2774 if (I.isPackExpansion())2775 OS << "...";2776 });2777 }2778}2779 2780void TextNodeDumper::VisitFunctionTemplateDecl(const FunctionTemplateDecl *D) {2781 dumpName(D);2782}2783 2784void TextNodeDumper::VisitClassTemplateDecl(const ClassTemplateDecl *D) {2785 dumpName(D);2786}2787 2788void TextNodeDumper::VisitVarTemplateDecl(const VarTemplateDecl *D) {2789 dumpName(D);2790}2791 2792void TextNodeDumper::VisitBuiltinTemplateDecl(const BuiltinTemplateDecl *D) {2793 dumpName(D);2794}2795 2796void TextNodeDumper::VisitTemplateTypeParmDecl(const TemplateTypeParmDecl *D) {2797 if (const auto *TC = D->getTypeConstraint()) {2798 OS << " ";2799 dumpBareDeclRef(TC->getNamedConcept());2800 if (TC->getNamedConcept() != TC->getFoundDecl()) {2801 OS << " (";2802 dumpBareDeclRef(TC->getFoundDecl());2803 OS << ")";2804 }2805 } else if (D->wasDeclaredWithTypename())2806 OS << " typename";2807 else2808 OS << " class";2809 OS << " depth " << D->getDepth() << " index " << D->getIndex();2810 if (D->isParameterPack())2811 OS << " ...";2812 dumpName(D);2813}2814 2815void TextNodeDumper::VisitNonTypeTemplateParmDecl(2816 const NonTypeTemplateParmDecl *D) {2817 dumpType(D->getType());2818 OS << " depth " << D->getDepth() << " index " << D->getIndex();2819 if (D->isParameterPack())2820 OS << " ...";2821 dumpName(D);2822}2823 2824void TextNodeDumper::VisitTemplateTemplateParmDecl(2825 const TemplateTemplateParmDecl *D) {2826 OS << " depth " << D->getDepth() << " index " << D->getIndex();2827 if (D->isParameterPack())2828 OS << " ...";2829 dumpName(D);2830}2831 2832void TextNodeDumper::VisitUsingDecl(const UsingDecl *D) {2833 OS << ' ';2834 D->getQualifier().print(OS, D->getASTContext().getPrintingPolicy());2835 OS << D->getDeclName();2836 dumpNestedNameSpecifier(D->getQualifier());2837}2838 2839void TextNodeDumper::VisitUsingEnumDecl(const UsingEnumDecl *D) {2840 OS << ' ';2841 dumpBareDeclRef(D->getEnumDecl());2842}2843 2844void TextNodeDumper::VisitUnresolvedUsingTypenameDecl(2845 const UnresolvedUsingTypenameDecl *D) {2846 OS << ' ';2847 D->getQualifier().print(OS, D->getASTContext().getPrintingPolicy());2848 OS << D->getDeclName();2849}2850 2851void TextNodeDumper::VisitUnresolvedUsingValueDecl(2852 const UnresolvedUsingValueDecl *D) {2853 OS << ' ';2854 D->getQualifier().print(OS, D->getASTContext().getPrintingPolicy());2855 OS << D->getDeclName();2856 dumpType(D->getType());2857}2858 2859void TextNodeDumper::VisitUsingShadowDecl(const UsingShadowDecl *D) {2860 OS << ' ';2861 dumpBareDeclRef(D->getTargetDecl());2862}2863 2864void TextNodeDumper::VisitConstructorUsingShadowDecl(2865 const ConstructorUsingShadowDecl *D) {2866 if (D->constructsVirtualBase())2867 OS << " virtual";2868 2869 AddChild([=] {2870 OS << "target ";2871 dumpBareDeclRef(D->getTargetDecl());2872 });2873 2874 AddChild([=] {2875 OS << "nominated ";2876 dumpBareDeclRef(D->getNominatedBaseClass());2877 OS << ' ';2878 dumpBareDeclRef(D->getNominatedBaseClassShadowDecl());2879 });2880 2881 AddChild([=] {2882 OS << "constructed ";2883 dumpBareDeclRef(D->getConstructedBaseClass());2884 OS << ' ';2885 dumpBareDeclRef(D->getConstructedBaseClassShadowDecl());2886 });2887}2888 2889void TextNodeDumper::VisitLinkageSpecDecl(const LinkageSpecDecl *D) {2890 switch (D->getLanguage()) {2891 case LinkageSpecLanguageIDs::C:2892 OS << " C";2893 break;2894 case LinkageSpecLanguageIDs::CXX:2895 OS << " C++";2896 break;2897 }2898}2899 2900void TextNodeDumper::VisitAccessSpecDecl(const AccessSpecDecl *D) {2901 OS << ' ';2902 dumpAccessSpecifier(D->getAccess());2903}2904 2905void TextNodeDumper::VisitFriendDecl(const FriendDecl *D) {2906 if (TypeSourceInfo *T = D->getFriendType())2907 dumpType(T->getType());2908 if (D->isPackExpansion())2909 OS << "...";2910}2911 2912void TextNodeDumper::VisitObjCIvarDecl(const ObjCIvarDecl *D) {2913 dumpName(D);2914 dumpType(D->getType());2915 if (D->getSynthesize())2916 OS << " synthesize";2917 2918 switch (D->getAccessControl()) {2919 case ObjCIvarDecl::None:2920 OS << " none";2921 break;2922 case ObjCIvarDecl::Private:2923 OS << " private";2924 break;2925 case ObjCIvarDecl::Protected:2926 OS << " protected";2927 break;2928 case ObjCIvarDecl::Public:2929 OS << " public";2930 break;2931 case ObjCIvarDecl::Package:2932 OS << " package";2933 break;2934 }2935}2936 2937void TextNodeDumper::VisitObjCMethodDecl(const ObjCMethodDecl *D) {2938 if (D->isInstanceMethod())2939 OS << " -";2940 else2941 OS << " +";2942 dumpName(D);2943 dumpType(D->getReturnType());2944 2945 if (D->isVariadic())2946 OS << " variadic";2947}2948 2949void TextNodeDumper::VisitObjCTypeParamDecl(const ObjCTypeParamDecl *D) {2950 dumpName(D);2951 switch (D->getVariance()) {2952 case ObjCTypeParamVariance::Invariant:2953 break;2954 2955 case ObjCTypeParamVariance::Covariant:2956 OS << " covariant";2957 break;2958 2959 case ObjCTypeParamVariance::Contravariant:2960 OS << " contravariant";2961 break;2962 }2963 2964 if (D->hasExplicitBound())2965 OS << " bounded";2966 dumpType(D->getUnderlyingType());2967}2968 2969void TextNodeDumper::VisitObjCCategoryDecl(const ObjCCategoryDecl *D) {2970 dumpName(D);2971 dumpDeclRef(D->getClassInterface());2972 dumpDeclRef(D->getImplementation());2973 for (const auto *P : D->protocols())2974 dumpDeclRef(P);2975}2976 2977void TextNodeDumper::VisitObjCCategoryImplDecl(const ObjCCategoryImplDecl *D) {2978 dumpName(D);2979 dumpDeclRef(D->getClassInterface());2980 dumpDeclRef(D->getCategoryDecl());2981}2982 2983void TextNodeDumper::VisitObjCProtocolDecl(const ObjCProtocolDecl *D) {2984 dumpName(D);2985 2986 for (const auto *Child : D->protocols())2987 dumpDeclRef(Child);2988}2989 2990void TextNodeDumper::VisitObjCInterfaceDecl(const ObjCInterfaceDecl *D) {2991 dumpName(D);2992 dumpDeclRef(D->getSuperClass(), "super");2993 2994 dumpDeclRef(D->getImplementation());2995 for (const auto *Child : D->protocols())2996 dumpDeclRef(Child);2997}2998 2999void TextNodeDumper::VisitObjCImplementationDecl(3000 const ObjCImplementationDecl *D) {3001 dumpName(D);3002 dumpDeclRef(D->getSuperClass(), "super");3003 dumpDeclRef(D->getClassInterface());3004}3005 3006void TextNodeDumper::VisitObjCCompatibleAliasDecl(3007 const ObjCCompatibleAliasDecl *D) {3008 dumpName(D);3009 dumpDeclRef(D->getClassInterface());3010}3011 3012void TextNodeDumper::VisitObjCPropertyDecl(const ObjCPropertyDecl *D) {3013 dumpName(D);3014 dumpType(D->getType());3015 3016 if (D->getPropertyImplementation() == ObjCPropertyDecl::Required)3017 OS << " required";3018 else if (D->getPropertyImplementation() == ObjCPropertyDecl::Optional)3019 OS << " optional";3020 3021 ObjCPropertyAttribute::Kind Attrs = D->getPropertyAttributes();3022 if (Attrs != ObjCPropertyAttribute::kind_noattr) {3023 if (Attrs & ObjCPropertyAttribute::kind_readonly)3024 OS << " readonly";3025 if (Attrs & ObjCPropertyAttribute::kind_assign)3026 OS << " assign";3027 if (Attrs & ObjCPropertyAttribute::kind_readwrite)3028 OS << " readwrite";3029 if (Attrs & ObjCPropertyAttribute::kind_retain)3030 OS << " retain";3031 if (Attrs & ObjCPropertyAttribute::kind_copy)3032 OS << " copy";3033 if (Attrs & ObjCPropertyAttribute::kind_nonatomic)3034 OS << " nonatomic";3035 if (Attrs & ObjCPropertyAttribute::kind_atomic)3036 OS << " atomic";3037 if (Attrs & ObjCPropertyAttribute::kind_weak)3038 OS << " weak";3039 if (Attrs & ObjCPropertyAttribute::kind_strong)3040 OS << " strong";3041 if (Attrs & ObjCPropertyAttribute::kind_unsafe_unretained)3042 OS << " unsafe_unretained";3043 if (Attrs & ObjCPropertyAttribute::kind_class)3044 OS << " class";3045 if (Attrs & ObjCPropertyAttribute::kind_direct)3046 OS << " direct";3047 if (Attrs & ObjCPropertyAttribute::kind_getter)3048 dumpDeclRef(D->getGetterMethodDecl(), "getter");3049 if (Attrs & ObjCPropertyAttribute::kind_setter)3050 dumpDeclRef(D->getSetterMethodDecl(), "setter");3051 }3052}3053 3054void TextNodeDumper::VisitObjCPropertyImplDecl(const ObjCPropertyImplDecl *D) {3055 dumpName(D->getPropertyDecl());3056 if (D->getPropertyImplementation() == ObjCPropertyImplDecl::Synthesize)3057 OS << " synthesize";3058 else3059 OS << " dynamic";3060 dumpDeclRef(D->getPropertyDecl());3061 dumpDeclRef(D->getPropertyIvarDecl());3062}3063 3064void TextNodeDumper::VisitBlockDecl(const BlockDecl *D) {3065 if (D->isVariadic())3066 OS << " variadic";3067 3068 if (D->capturesCXXThis())3069 OS << " captures_this";3070}3071 3072void TextNodeDumper::VisitConceptDecl(const ConceptDecl *D) {3073 dumpName(D);3074}3075 3076void TextNodeDumper::VisitCompoundStmt(const CompoundStmt *S) {3077 VisitStmt(S);3078 if (S->hasStoredFPFeatures())3079 printFPOptions(S->getStoredFPFeatures());3080}3081 3082void TextNodeDumper::VisitHLSLBufferDecl(const HLSLBufferDecl *D) {3083 if (D->isCBuffer())3084 OS << " cbuffer";3085 else3086 OS << " tbuffer";3087 dumpName(D);3088}3089 3090void TextNodeDumper::VisitHLSLRootSignatureDecl(3091 const HLSLRootSignatureDecl *D) {3092 dumpName(D);3093 OS << " version: ";3094 switch (D->getVersion()) {3095 case llvm::dxbc::RootSignatureVersion::V1_0:3096 OS << "1.0";3097 break;3098 case llvm::dxbc::RootSignatureVersion::V1_1:3099 OS << "1.1";3100 break;3101 case llvm::dxbc::RootSignatureVersion::V1_2:3102 OS << "1.2";3103 break;3104 }3105 OS << ", ";3106 llvm::hlsl::rootsig::dumpRootElements(OS, D->getRootElements());3107}3108 3109void TextNodeDumper::VisitHLSLOutArgExpr(const HLSLOutArgExpr *E) {3110 OS << (E->isInOut() ? " inout" : " out");3111}3112 3113void TextNodeDumper::VisitOpenACCConstructStmt(const OpenACCConstructStmt *S) {3114 OS << " " << S->getDirectiveKind();3115}3116void TextNodeDumper::VisitOpenACCLoopConstruct(const OpenACCLoopConstruct *S) {3117 if (S->isOrphanedLoopConstruct())3118 OS << " <orphan>";3119 else3120 OS << " parent: " << S->getParentComputeConstructKind();3121}3122 3123void TextNodeDumper::VisitOpenACCCombinedConstruct(3124 const OpenACCCombinedConstruct *S) {3125 VisitOpenACCConstructStmt(S);3126}3127 3128void TextNodeDumper::VisitOpenACCDataConstruct(const OpenACCDataConstruct *S) {3129 VisitOpenACCConstructStmt(S);3130}3131 3132void TextNodeDumper::VisitOpenACCEnterDataConstruct(3133 const OpenACCEnterDataConstruct *S) {3134 VisitOpenACCConstructStmt(S);3135}3136 3137void TextNodeDumper::VisitOpenACCExitDataConstruct(3138 const OpenACCExitDataConstruct *S) {3139 VisitOpenACCConstructStmt(S);3140}3141 3142void TextNodeDumper::VisitOpenACCHostDataConstruct(3143 const OpenACCHostDataConstruct *S) {3144 VisitOpenACCConstructStmt(S);3145}3146 3147void TextNodeDumper::VisitOpenACCWaitConstruct(const OpenACCWaitConstruct *S) {3148 VisitOpenACCConstructStmt(S);3149}3150void TextNodeDumper::VisitOpenACCCacheConstruct(3151 const OpenACCCacheConstruct *S) {3152 VisitOpenACCConstructStmt(S);3153 if (S->hasReadOnly())3154 OS <<" readonly";3155}3156void TextNodeDumper::VisitOpenACCInitConstruct(const OpenACCInitConstruct *S) {3157 VisitOpenACCConstructStmt(S);3158}3159void TextNodeDumper::VisitOpenACCShutdownConstruct(3160 const OpenACCShutdownConstruct *S) {3161 VisitOpenACCConstructStmt(S);3162}3163void TextNodeDumper::VisitOpenACCSetConstruct(const OpenACCSetConstruct *S) {3164 VisitOpenACCConstructStmt(S);3165}3166void TextNodeDumper::VisitOpenACCUpdateConstruct(3167 const OpenACCUpdateConstruct *S) {3168 VisitOpenACCConstructStmt(S);3169}3170 3171void TextNodeDumper::VisitOpenACCAtomicConstruct(3172 const OpenACCAtomicConstruct *S) {3173 VisitOpenACCConstructStmt(S);3174 OS << ' ' << S->getAtomicKind();3175}3176 3177void TextNodeDumper::VisitOpenACCDeclareDecl(const OpenACCDeclareDecl *D) {3178 OS << " " << D->getDirectiveKind();3179 3180 for (const OpenACCClause *C : D->clauses())3181 AddChild([=] {3182 Visit(C);3183 for (const Stmt *S : C->children())3184 AddChild([=] { Visit(S); });3185 });3186}3187void TextNodeDumper::VisitOpenACCRoutineDecl(const OpenACCRoutineDecl *D) {3188 OS << " " << D->getDirectiveKind();3189 3190 dumpSourceRange(SourceRange{D->getLParenLoc(), D->getRParenLoc()});3191 3192 AddChild([=] { Visit(D->getFunctionReference()); });3193 3194 for (const OpenACCClause *C : D->clauses())3195 AddChild([=] {3196 Visit(C);3197 for (const Stmt *S : C->children())3198 AddChild([=] { Visit(S); });3199 });3200}3201 3202void TextNodeDumper::VisitOpenACCRoutineDeclAttr(3203 const OpenACCRoutineDeclAttr *A) {3204 for (const OpenACCClause *C : A->Clauses)3205 AddChild([=] {3206 Visit(C);3207 for (const Stmt *S : C->children())3208 AddChild([=] { Visit(S); });3209 });3210}3211 3212void TextNodeDumper::VisitEmbedExpr(const EmbedExpr *S) {3213 AddChild("begin", [=] { OS << S->getStartingElementPos(); });3214 AddChild("number of elements", [=] { OS << S->getDataElementCount(); });3215}3216 3217void TextNodeDumper::VisitAtomicExpr(const AtomicExpr *AE) {3218 OS << ' ' << AE->getOpAsString();3219}3220 3221void TextNodeDumper::VisitConvertVectorExpr(const ConvertVectorExpr *S) {3222 VisitStmt(S);3223 if (S->hasStoredFPFeatures())3224 printFPOptions(S->getStoredFPFeatures());3225}3226