clang: lib/ExtractAPI/DeclarationFragments.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

13

24#include "llvm/ADT/StringSwitch.h"

25#include "llvm/Support/ErrorHandling.h"

26#include "llvm/Support/raw_ostream.h"

27#include

28

30using namespace llvm;

31

32namespace {

33

37 if (!TSInfo)

38 return;

39

41 while (true) {

42

45 continue;

46 }

47

49 TL = AttrTL.getModifiedLoc();

50 continue;

51 }

52

53

54

59 }

60 break;

61 }

62}

63

64}

65

67DeclarationFragments::appendUnduplicatedTextCharacter(char Character) {

68 if (!Fragments.empty()) {

69 Fragment &Last = Fragments.back();

71

72

73 if (Last.Spelling.back() != Character) {

74 Last.Spelling.push_back(Character);

75 }

76 } else {

78 Fragments.back().Spelling.push_back(Character);

79 }

80 }

81

82 return *this;

83}

84

86 return appendUnduplicatedTextCharacter(' ');

87}

88

90 return appendUnduplicatedTextCharacter(';');

91}

92

94 if (Fragments.empty())

95 return *this;

96

99 Last.Spelling.pop_back();

100

101 return *this;

102}

103

106 switch (Kind) {

108 return "none";

110 return "keyword";

112 return "attribute";

114 return "number";

116 return "string";

118 return "identifier";

120 return "typeIdentifier";

122 return "genericParameter";

124 return "externalParam";

126 return "internalParam";

128 return "text";

129 }

130

131 llvm_unreachable("Unhandled FragmentKind");

132}

133

136 return llvm::StringSwitch(S)

142 .Case("typeIdentifier",

144 .Case("genericParameter",

150}

151

155 switch (ExceptionSpec) {

157 return Fragments;

164

165 return Fragments;

170

171 break;

184 default:

185 return Fragments;

186 }

187

188 llvm_unreachable("Unhandled exception specification");

189}

190

194 if (Record->isStruct())

196 else if (Record->isUnion())

198 else

200

201 return Fragments;

202}

203

204

205

206

207

209DeclarationFragmentsBuilder::getFragmentsForNNS(const NestedNameSpecifier *NNS,

214 Fragments.append(getFragmentsForNNS(NNS->getPrefix(), Context, After));

215

216 switch (NNS->getKind()) {

220 break;

221

225 return Fragments;

230 break;

231 }

232

237 Fragments.append(Alias->getName(),

239 Alias);

240 break;

241 }

242

244

245 break;

246

248

250 break;

251

253

256

257 [[fallthrough]];

258

261

262 Fragments.append(getFragmentsForType(T, Context, After));

263 break;

264 }

265 }

266

267

269}

270

271

272

275 assert(T && "invalid type");

276

278

281 getFragmentsForType(MQT->getUnderlyingType(), Context, After));

282 return Fragments;

283 }

284

285 if (const AttributedType *AT = dyn_cast(T)) {

286

288 getFragmentsForType(AT->getModifiedType(), Context, After));

289 return Fragments;

290 }

291

292

293

294

295 if (const ElaboratedType *ET = dyn_cast(T)) {

298 Fragments

302 }

303

305 Fragments.append(getFragmentsForNNS(NNS, Context, After));

306

307

308

309 return Fragments.append(getFragmentsForType(ET->desugar(), Context, After));

310 }

311

312

313

314

315

316

317 if (const TypedefType *TypedefTy = dyn_cast(T)) {

320 std::string USR = TypedefResolver.getUSRForType(QualType(T, 0));

321

323 return Fragments.append(Decl->getName(),

325 }

326

327 return Fragments.append(

329 USR, TypedefResolver.getUnderlyingTypeDecl(QualType(T, 0)));

330 }

331

332

333

335 return Fragments

338

339

340

343

345

346

347

350 }

351

352 return Fragments;

353 }

354

355

356

358 return Fragments

360 getFragmentsForType(LRT->getPointeeTypeAsWritten(), Context, After))

362

363

364

366 return Fragments

368 getFragmentsForType(RRT->getPointeeTypeAsWritten(), Context, After))

370

371

372

373

375

376

377

378

380

381 switch (AT->getSizeModifier()) {

383 break;

386 break;

389 break;

390 }

391

392 if (const ConstantArrayType *CAT = dyn_cast(AT)) {

393

394

395

396

398 CAT->getSize().toStringUnsigned(Size);

400 }

401

403

404 return Fragments.append(

405 getFragmentsForType(AT->getElementType(), Context, After));

406 }

407

409 dyn_cast(T)) {

410 const auto TemplName = TemplSpecTy->getTemplateName();

411 std::string Str;

412 raw_string_ostream Stream(Str);

413 TemplName.print(Stream, Context.getPrintingPolicy(),

416 if (const auto *TemplDecl = TemplName.getAsTemplateDecl())

418

419 return Fragments

423 TemplSpecTy->template_arguments(), Context, std::nullopt))

425 }

426

427

428

430

431

432

433 if (const TagType *TagTy = dyn_cast(Base)) {

435

436 if (Decl->getName().empty())

437 return Fragments.append("{ ... }",

441 return Fragments.append(Decl->getName(),

443 TagUSR, Decl);

444 }

445

446

447

448 if (const auto *ObjCIT = dyn_cast(Base)) {

449 const auto *Decl = ObjCIT->getDecl();

452 return Fragments.append(Decl->getName(),

455 }

456

457

462

463 return Fragments;

464}

465

467DeclarationFragmentsBuilder::getFragmentsForQualifiers(const Qualifiers Quals) {

475

476 return Fragments;

477}

478

481 assert(!QT.isNull() && "invalid type");

482

483 if (const ParenType *PT = dyn_cast(QT)) {

485 return getFragmentsForType(PT->getInnerType(), Context, After)

487 }

488

491 TypeFragments =

492 getFragmentsForType(SQT.Ty, Context, After);

494 TypeFragments.replace("bool", 0);

495

497 return TypeFragments;

498

499

500

501

502

503

504

505

506

507

508

509

510

511

512

513

514

515

517 return TypeFragments.appendSpace().append(std::move(QualsFragments));

518

519 return QualsFragments.appendSpace().append(std::move(TypeFragments));

520}

521

526 if (Decl->isAnonymousNamespace())

530}

531

538

541 Fragments

545

546

547

548

549

550

554 findTypeLocForBlockDecl(Var->getTypeSourceInfo(), BlockLoc, BlockProtoLoc);

555

556 if (!BlockLoc) {

561

564 } else {

565 Fragments.append(getFragmentsForBlock(Var, BlockLoc, BlockProtoLoc, After));

566 }

567

568 return Fragments

570 .append(std::move(After))

572}

573

584

585

589

593 if (StringRef(ArgumentFragment.begin()->Spelling)

594 .starts_with("type-parameter")) {

595 std::string ProperArgName = T.getAsString();

596 ArgumentFragment.begin()->Spelling.swap(ProperArgName);

597 }

598 Fragments.append(std::move(ArgumentFragment))

602 return Fragments;

603}

604

606DeclarationFragmentsBuilder::getFragmentsForParam(const ParmVarDecl *Param) {

608

610

614

617 findTypeLocForBlockDecl(TSInfo, BlockLoc, BlockProtoLoc);

618

620 if (BlockLoc)

621 TypeFragments.append(

622 getFragmentsForBlock(Param, BlockLoc, BlockProtoLoc, After));

623 else

625

626 if (StringRef(TypeFragments.begin()->Spelling)

627 .starts_with("type-parameter")) {

629 TypeFragments.begin()->Spelling.swap(ProperArgName);

630 }

631

634 .append(std::move(TypeFragments))

635 .append(std::move(After))

639 } else {

640 Fragments.append(std::move(TypeFragments));

643 Fragments

646 .append(std::move(After));

647 }

648 return Fragments;

649}

650

655

657 auto ReturnValueFragment = getFragmentsForType(

659

660 Fragments.append(std::move(ReturnValueFragment))

661 .append(std::move(RetTyAfter))

664

666 unsigned NumParams = Block.getNumParams();

667

668 if (!BlockProto || NumParams == 0) {

671 else

673 } else {

675 for (unsigned I = 0; I != NumParams; ++I) {

676 if (I)

678 After.append(getFragmentsForParam(Block.getParam(I)));

681 }

683 }

684

685 return Fragments;

686}

687

691 switch (Func->getStorageClass()) {

694 break;

698 break;

702 break;

705 llvm_unreachable("invalid for functions");

706 }

707 if (Func->isConsteval())

710 else if (Func->isConstexpr())

713

714

716 auto ReturnValueFragment =

717 getFragmentsForType(Func->getReturnType(), Func->getASTContext(), After);

718 if (StringRef(ReturnValueFragment.begin()->Spelling)

719 .starts_with("type-parameter")) {

720 std::string ProperArgName = Func->getReturnType().getAsString();

721 ReturnValueFragment.begin()->Spelling.swap(ProperArgName);

722 }

723

724 Fragments.append(std::move(ReturnValueFragment))

728

729 if (Func->getTemplateSpecializationInfo()) {

731

732 for (unsigned i = 0, end = Func->getNumParams(); i != end; ++i) {

733 if (i)

736 getFragmentsForType(Func->getParamDecl(i)->getType(),

737 Func->getParamDecl(i)->getASTContext(), After));

738 }

740 }

741 Fragments.append(std::move(After));

742

744 unsigned NumParams = Func->getNumParams();

745 for (unsigned i = 0; i != NumParams; ++i) {

746 if (i)

748 Fragments.append(getFragmentsForParam(Func->getParamDecl(i)));

749 }

750

751 if (Func->isVariadic()) {

752 if (NumParams > 0)

755 }

757

759 Func->getExceptionSpecType()));

760

762}

763

767 return Fragments.append(EnumConstDecl->getName(),

769}

770

775

778

782

784 if (!IntegerType.isNull())

789 .append(std::move(After));

790

794

796}

797

802 if (Field->isMutable())

805 return Fragments

807 getFragmentsForType(Field->getType(), Field->getASTContext(), After))

810 .append(std::move(After))

812}

813

818

820 if (Record->isUnion())

822 else

824

826 if (Record->getName().empty())

829 else

831

833}

834

839

842

843 if (Record->getName().empty())

846

848}

849

854 std::string Name;

855 if (const auto *Constructor = dyn_cast(Method)) {

857 if (Constructor->isExplicit())

860 } else if (isa(Method))

862

865 .append(std::move(After));

867 for (unsigned i = 0, end = Method->getNumParams(); i != end; ++i) {

868 if (i)

871 }

873

876

878}

879

883 StringRef Name = Method->getName();

893

894

896 Fragments

901 .append(std::move(After));

903 for (unsigned i = 0, end = Method->getNumParams(); i != end; ++i) {

904 if (i)

907 }

909

913

916

918}

919

924

925 if (ConversionFunction->isExplicit())

928

931

932 Fragments

933 .append(ConversionFunction->getConversionType().getAsString(),

936 for (unsigned i = 0, end = ConversionFunction->getNumParams(); i != end;

937 ++i) {

938 if (i)

940 Fragments.append(getFragmentsForParam(ConversionFunction->getParamDecl(i)));

941 }

943

944 if (ConversionFunction->isConst())

947

949}

950

955

956

958 Fragments

964 .append(std::move(After));

966 for (unsigned i = 0, end = Method->getNumParams(); i != end; ++i) {

967 if (i)

970 }

972

976

979

981}

982

983

988 for (unsigned i = 0, end = ParameterArray.size(); i != end; ++i) {

989 if (i)

992

994 dyn_cast(ParameterArray[i])) {

997 ->getNamedConcept()

998 ->getName()

999 .str(),

1001 else if (TemplateParam->wasDeclaredWithTypename())

1002 Fragments.append("typename",

1004 else

1006

1009

1014

1021 }

1022 } else if (const auto *NTP =

1023 dyn_cast(ParameterArray[i])) {

1025 const auto TyFragments =

1026 getFragmentsForType(NTP->getType(), NTP->getASTContext(), After);

1027 Fragments.append(std::move(TyFragments)).append(std::move(After));

1028

1029 if (NTP->isParameterPack())

1031

1032 if (!NTP->getName().empty())

1034 NTP->getName(),

1036

1037 if (NTP->hasDefaultArgument()) {

1039 raw_svector_ostream Output(ExprStr);

1040 NTP->getDefaultArgument().getArgument().print(

1041 NTP->getASTContext().getPrintingPolicy(), Output,

1042 false);

1045 }

1046 } else if (const auto *TTP =

1047 dyn_cast(ParameterArray[i])) {

1052 TTP->getTemplateParameters()->asArray()))

1055 .append(TTP->wasDeclaredWithTypename() ? "typename" : "class",

1057

1058 if (TTP->isParameterPack())

1060

1061 if (!TTP->getName().empty())

1063 TTP->getName(),

1065 if (TTP->hasDefaultArgument()) {

1066 const auto Default = TTP->getDefaultArgument();

1069 {Default.getArgument()}, TTP->getASTContext(), {Default}));

1070 }

1071 }

1072 }

1073 return Fragments;

1074}

1075

1076

1077

1078

1079

1080

1081

1087 for (unsigned i = 0, end = TemplateArguments.size(); i != end; ++i) {

1088 if (i)

1091

1092 const auto &CTA = TemplateArguments[i];

1093 switch (CTA.getKind()) {

1097 getFragmentsForType(CTA.getAsType(), Context, After);

1098

1099 if (StringRef(ArgumentFragment.begin()->Spelling)

1100 .starts_with("type-parameter")) {

1101 if (TemplateArgumentLocs.has_value() &&

1102 TemplateArgumentLocs->size() > i) {

1103 std::string ProperArgName = TemplateArgumentLocs.value()[i]

1104 .getTypeSourceInfo()

1105 ->getType()

1106 .getAsString();

1107 ArgumentFragment.begin()->Spelling.swap(ProperArgName);

1108 } else {

1109 auto &Spelling = ArgumentFragment.begin()->Spelling;

1110 Spelling.clear();

1111 raw_string_ostream OutStream(Spelling);

1112 CTA.print(Context.getPrintingPolicy(), OutStream, false);

1113 }

1114 }

1115

1116 Fragments.append(std::move(ArgumentFragment));

1117 break;

1118 }

1120 const auto *VD = CTA.getAsDecl();

1123 Fragments.append(VD->getNameAsString(),

1125 break;

1126 }

1129 break;

1130

1133 CTA.getAsIntegral().toString(Str);

1135 break;

1136 }

1137

1139 const auto SVTy = CTA.getStructuralValueType();

1140 Fragments.append(CTA.getAsStructuralValue().getAsString(Context, SVTy),

1142 break;

1143 }

1144

1147 std::string Str;

1148 raw_string_ostream Stream(Str);

1149 CTA.getAsTemplate().print(Stream, Context.getPrintingPolicy());

1151 if (const auto *TemplDecl =

1152 CTA.getAsTemplateOrTemplatePattern().getAsTemplateDecl())

1155 USR);

1158 break;

1159 }

1160

1164 {}))

1166 break;

1167

1170 raw_svector_ostream Output(ExprStr);

1171 CTA.getAsExpr()->printPretty(Output, nullptr,

1172 Context.getPrintingPolicy());

1174 break;

1175 }

1176

1178 break;

1179 }

1180 }

1181 return Fragments;

1182}

1183

1187 return Fragments

1192 Concept->getTemplateParameters()->asArray()))

1197 .append(Concept->getName().str(),

1200}

1201

1213

1214 if (isa(RedeclarableTemplate))

1220

1222}

1223

1228 return Fragments

1235 cast(Decl)))

1236 .pop_back()

1240 Decl->getTemplateArgsAsWritten()->arguments()))

1243}

1244

1249 return Fragments

1254 Decl->getTemplateParameters()->asArray()))

1258 cast(Decl)))

1259 .pop_back()

1263 Decl->getTemplateArgsAsWritten()->arguments()))

1266}

1267

1272 return Fragments

1279 .pop_back()

1283 Decl->getTemplateArgsAsWritten()->arguments()))

1286}

1287

1292 return Fragments

1296

1298 Decl->getTemplateParameters()->asArray()))

1302 .pop_back()

1306 Decl->getTemplateArgsAsWritten()->arguments()))

1309}

1310

1315 return Fragments

1319

1321 Decl->getTemplateParameters()->asArray()))

1326}

1327

1332 return Fragments

1338}

1339

1347

1350 unsigned numParameters = MI->getNumParams();

1352 --numParameters;

1353 for (unsigned i = 0; i < numParameters; ++i) {

1354 if (i)

1356 Fragments.append(MI->params()[i]->getName(),

1358 }

1363 }

1365 }

1366 return Fragments;

1367}

1368

1372

1376

1386

1387 return Fragments;

1388}

1389

1393

1398

1399

1404 .append(SuperClass->getName(),

1406 SuperClass);

1407 }

1408

1409 return Fragments;

1410}

1411

1415

1420

1421

1425 .append(std::move(After))

1427

1428

1431

1432

1436

1437

1438 for (unsigned i = 0, end = Method->param_size(); i != end; ++i) {

1439

1440

1441

1442

1444 ParamID.append(":");

1447

1448

1450 Fragments.append(getFragmentsForParam(Param));

1451 }

1452

1454}

1455

1459

1460

1462

1463 const auto Attributes = Property->getPropertyAttributesAsWritten();

1464

1466

1467 bool First = true;

1469

1470 auto RenderAttribute =

1472 StringRef Arg = "",

1475

1476 if ((Attributes & Kind) && !Spelling.empty()) {

1477

1480

1481 Fragments.append(Spelling,

1483

1484

1485 if (!Arg.empty())

1487 .append(Arg, ArgKind);

1489 }

1490 };

1491

1492

1493

1504 "unsafe_unretained");

1508 Property->getGetterName().getAsString());

1510 Property->getSetterName().getAsString());

1511

1512

1515 if (const auto Nullability =

1521 Fragments.append("null_resettable",

1523 else

1528 }

1529 }

1530

1532 }

1533

1535

1538 findTypeLocForBlockDecl(Property->getTypeSourceInfo(), BlockLoc,

1539 BlockProtoLoc);

1540

1541 auto PropType = Property->getType();

1542 if (!BlockLoc)

1543 Fragments

1544 .append(getFragmentsForType(PropType, Property->getASTContext(), After))

1546 else

1548 getFragmentsForBlock(Property, BlockLoc, BlockProtoLoc, After));

1549

1550 return Fragments

1553 .append(std::move(After))

1555}

1556

1560

1563 .append(Protocol->getName(),

1565

1566

1567 if (!Protocol->protocols().empty()) {

1570 It != Protocol->protocol_end(); It++) {

1571

1572 if (It != Protocol->protocol_begin())

1574

1577 Fragments.append((*It)->getName(),

1579 *It);

1580 }

1582 }

1583

1584 return Fragments;

1585}

1586

1592 .append(getFragmentsForType(Decl->getUnderlyingType(),

1594 .append(std::move(After))

1597

1599}

1600

1601

1604

1605

1608

1609

1613 if (isa(Decl) || isa(Decl))

1616 else if (isa(Decl)) {

1618 cast(Decl)->getConversionType().getAsString(),

1620 } else if (isa(Decl) &&

1621 cast(Decl)->isOverloadedOperator()) {

1622 Fragments.append(Decl->getNameAsString(),

1624 } else if (isa(Decl) &&

1625 cast(Decl)->getTypedefNameForAnonDecl()) {

1626 return getSubHeading(cast(Decl)->getTypedefNameForAnonDecl());

1627 } else if (Decl->getIdentifier()) {

1630 } else

1631 Fragments.append(Decl->getDeclName().getAsString(),

1633 return Fragments;

1634}

1635

1636

1637

1645

1648}

1649

1650

1655 return Fragments;

1656}

Forward declaration of all AST node types.

Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....

This file defines the Declaration Fragments related classes.

llvm::MachO::Record Record

Defines the clang::TypeLoc interface and its subclasses.

C Language Family Type Representation.

This file defines the UnderlyingTypeResolver which is a helper type for resolving the undelrying type...

Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...

QualType getUnqualifiedObjCPointerType(QualType type) const

getUnqualifiedObjCPointerType - Returns version of Objective-C pointer type with lifetime qualifier r...

Represents an array type, per C99 6.7.5.2 - Array Declarators.

Type source information for an attributed type.

An attributed type is a type to which a type attribute has been applied.

static std::optional< NullabilityKind > stripOuterNullability(QualType &T)

Strip off the top-level nullability annotation on the given type, if it's there.

Represents a block literal declaration, which is like an unnamed FunctionDecl.

Wrapper for source info for block pointers.

Represents a C++ conversion function within a class.

Represents a static or instance method of a struct/union/class.

Represents a C++ struct/union/class.

Represents a class template specialization, which refers to a class template with a given set of temp...

Declaration of a C++20 concept.

Represents the canonical version of C arrays with a specified constant size.

Decl - This represents one declaration (or definition), e.g.

ASTContext & getASTContext() const LLVM_READONLY

FunctionDecl * getAsFunction() LLVM_READONLY

Returns the function itself, or the templated function if this is a function template.

DeclContext * getDeclContext()

TypeSourceInfo * getTypeSourceInfo() const

Represents a type that was referred to using an elaborated type keyword, e.g., struct S,...

An instance of this object exists for each enum constant that is defined.

QualType getIntegerType() const

Return the integer type this enum decl corresponds to.

Represents a member of a struct/union/class.

Represents a function declaration or definition.

const ParmVarDecl * getParamDecl(unsigned i) const

ExceptionSpecificationType getExceptionSpecType() const

Gets the ExceptionSpecificationType as declared.

QualType getReturnType() const

bool isConstexpr() const

Whether this is a (C++11) constexpr function or constexpr constructor.

unsigned getNumParams() const

Return the number of parameters this function must have based on its FunctionType.

bool isVariadic() const

Whether this function prototype is variadic.

Declaration of a template function.

Wrapper for source info for functions.

StringRef getName() const

Return the actual identifier string.

const TypeClass * getTypePtr() const

An lvalue reference type, per C++11 [dcl.ref].

Encapsulates the data about a macro definition (e.g.

bool isC99Varargs() const

bool isFunctionLike() const

ArrayRef< const IdentifierInfo * > params() const

unsigned getNumParams() const

Sugar type that represents a type that was qualified by a qualifier written as a macro invocation.

This represents a decl that may have a name.

StringRef getName() const

Get the name of identifier for this declaration as a StringRef.

std::string getNameAsString() const

Get a human-readable name for the declaration, even if it is one of the special kinds of names (C++ c...

Represents a C++ namespace alias.

Represent a C++ namespace.

bool isAnonymousNamespace() const

Returns true if this is an anonymous namespace declaration.

Represents a C++ nested name specifier, such as "\::std::vector::".

SpecifierKind getKind() const

Determine what kind of nested name specifier is stored.

NamespaceAliasDecl * getAsNamespaceAlias() const

Retrieve the namespace alias stored in this nested name specifier.

IdentifierInfo * getAsIdentifier() const

Retrieve the identifier stored in this nested name specifier.

NestedNameSpecifier * getPrefix() const

Return the prefix of this nested name specifier.

@ NamespaceAlias

A namespace alias, stored as a NamespaceAliasDecl*.

@ TypeSpec

A type, stored as a Type*.

@ TypeSpecWithTemplate

A type that was preceded by the 'template' keyword, stored as a Type*.

@ Super

Microsoft's '__super' specifier, stored as a CXXRecordDecl* of the class it appeared in.

@ Identifier

An identifier, stored as an IdentifierInfo*.

@ Global

The global specifier '::'. There is no stored value.

@ Namespace

A namespace, stored as a NamespaceDecl*.

NamespaceDecl * getAsNamespace() const

Retrieve the namespace stored in this nested name specifier.

const Type * getAsType() const

Retrieve the type stored in this nested name specifier.

ObjCCategoryDecl - Represents a category declaration.

Represents an ObjC class declaration.

ObjCMethodDecl - Represents an instance or class method declaration.

unsigned param_size() const

Selector getSelector() const

bool isInstanceMethod() const

ParmVarDecl * getParamDecl(unsigned Idx)

QualType getReturnType() const

bool isClassMethod() const

Represents a pointer to an Objective C object.

bool isObjCQualifiedIdType() const

True if this is equivalent to 'id.

bool isObjCIdOrClassType() const

True if this is equivalent to the 'id' or 'Class' type,.

Represents one property declaration in an Objective-C interface.

Represents an Objective-C protocol declaration.

ObjCProtocolList::iterator protocol_iterator

Sugar for parentheses used when specifying types.

Represents a parameter to a function.

bool isObjCMethodParameter() const

QualType getOriginalType() const

A (possibly-)qualified type.

bool isNull() const

Return true if this QualType doesn't point to a type yet.

SplitQualType split() const

Divides a QualType into its unqualified type and a set of local qualifiers.

static std::string getAsString(SplitQualType split, const PrintingPolicy &Policy)

Wrapper of type source information for a type with non-trivial direct qualifiers.

The collection of all-type qualifiers we support.

An rvalue reference type, per C++11 [dcl.ref].

Represents a struct/union/class.

Declaration of a redeclarable template.

Smart pointer class that efficiently represents Objective-C method names.

StringRef getNameForSlot(unsigned argIndex) const

Retrieve the name at a given position in the selector.

unsigned getNumArgs() const

Represents the declaration of a struct/union/class/enum.

TypedefNameDecl * getTypedefNameForAnonDecl() const

@ Declaration

The template argument is a declaration that was provided for a pointer, reference,...

@ Template

The template argument is a template name that was provided for a template template parameter.

@ StructuralValue

The template argument is a non-type template argument that can't be represented by the special-case D...

@ Pack

The template argument is actually a parameter pack.

@ TemplateExpansion

The template argument is a pack expansion of a template name that was provided for a template templat...

@ NullPtr

The template argument is a null pointer or null pointer to member that was provided for a non-type te...

@ Type

The template argument is a type.

@ Null

Represents an empty template argument, e.g., one that has not been deduced.

@ Integral

The template argument is an integral value stored in an llvm::APSInt that was provided for an integra...

@ Expression

The template argument is an expression, and we've not resolved it to one of the other forms yet,...

TemplateParameterList * getTemplateParameters() const

Get the list of template parameters.

ArrayRef< NamedDecl * > asArray()

Represents a type template specialization; the template must be a class template, a type alias templa...

Base wrapper for a particular "section" of type source info.

UnqualTypeLoc getUnqualifiedLoc() const

Skips past any qualifiers, if this is qualified.

T getAs() const

Convert to the specified TypeLoc type, returning a null TypeLoc if this TypeLoc is not of the desired...

TypeLoc IgnoreParens() const

A container of type source information.

TypeLoc getTypeLoc() const

Return the TypeLoc wrapper for the type source info.

QualType getType() const

Return the type wrapped by this type source info.

static StringRef getKeywordName(ElaboratedTypeKeyword Keyword)

The base class of the type hierarchy.

bool isBlockPointerType() const

bool isFunctionPointerType() const

bool isPointerType() const

CanQualType getCanonicalTypeUnqualified() const

QualType getPointeeType() const

If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.

bool isObjCIdType() const

const ArrayType * getAsArrayTypeUnsafe() const

A variant of getAs<> for array types which silently discards qualifiers from the outermost type.

bool isObjCObjectPointerType() const

bool isAnyPointerType() const

const T * getAs() const

Member-template getAs'.

Base class for declarations which introduce a typedef-name.

Represents a variable declaration or definition.

bool isConstexpr() const

Whether this variable is (C++11) constexpr.

static const char * getStorageClassSpecifierString(StorageClass SC)

Return the string used to specify the storage class SC.

bool isStaticDataMember() const

Determines whether this is a static data member.

StorageClass getStorageClass() const

Returns the storage class as written in the source.

Represents a variable template specialization, which refers to a variable template with a given set o...

@ kind_nullability

Indicates that the nullability of the type was spelled with a property attribute rather than a type q...

@ After

Like System, but searched after the system directories.

bool generateUSRForType(QualType T, ASTContext &Ctx, SmallVectorImpl< char > &Buf)

Generates a USR for a type.

bool generateUSRForDecl(const Decl *D, SmallVectorImpl< char > &Buf)

Generate a USR for a Decl, including the USR prefix.

@ Unspecified

Whether values of this type can be null is (explicitly) unspecified.

StorageClass

Storage classes.

@ Property

The type of a property.

llvm::StringRef getNullabilitySpelling(NullabilityKind kind, bool isContextSensitive=false)

Retrieve the spelling of the given nullability kind.

const FunctionProtoType * T

llvm::StringRef getAsString(SyncScope S)

ElaboratedTypeKeyword

The elaboration keyword that precedes a qualified type name or introduces an elaborated-type-specifie...

@ Interface

The "__interface" keyword introduces the elaborated-type-specifier.

@ None

No keyword precedes the qualified type name.

ExceptionSpecificationType

The various types of exception specifications that exist in C++11.

@ EST_DependentNoexcept

noexcept(expression), value-dependent

@ EST_None

no exception specification

@ EST_BasicNoexcept

noexcept

@ EST_NoexceptFalse

noexcept(expression), evals to 'false'

@ EST_NoexceptTrue

noexcept(expression), evals to 'true'

@ EST_Dynamic

throw(T1, T2)

Diagnostic wrappers for TextAPI types for error reporting.

A std::pair-like structure for storing a qualified type split into its local qualifiers and its local...

const Type * Ty

The locally-unqualified type.

Qualifiers Quals

The local qualifiers.