clang 19.0.0git
DeclarationFragments.h
Go to the documentation of this file.
1//===- ExtractAPI/DeclarationFragments.h ------------------------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8///
9/// \file
10/// This file defines the Declaration Fragments related classes.
11///
12/// Declaration Fragments represent parts of a symbol declaration tagged with
13/// syntactic/semantic information.
14/// See https://github.com/apple/swift-docc-symbolkit
15///
16//===----------------------------------------------------------------------===//
17
18#ifndef LLVM_CLANG_EXTRACTAPI_DECLARATION_FRAGMENTS_H
19#define LLVM_CLANG_EXTRACTAPI_DECLARATION_FRAGMENTS_H
20
22#include "clang/AST/Decl.h"
23#include "clang/AST/DeclCXX.h"
24#include "clang/AST/DeclObjC.h"
26#include "clang/AST/ExprCXX.h"
27#include "clang/AST/TypeLoc.h"
29#include "clang/Lex/MacroInfo.h"
30#include <vector>
31
32namespace clang {
33namespace extractapi {
34
35/// DeclarationFragments is a vector of tagged important parts of a symbol's
36/// declaration.
37///
38/// The fragments sequence can be joined to form spans of declaration text, with
39/// attached information useful for purposes like syntax-highlighting etc.
40/// For example:
41/// \code
42/// const -> keyword "const"
43/// int -> type "int"
44/// pi; -> identifier "pi"
45/// \endcode
47public:
49
50 /// The kind of a fragment.
51 enum class FragmentKind {
52 /// Unknown fragment kind.
53 None,
54
55 Keyword,
60
61 /// Identifier that refers to a type in the context.
63
64 /// Parameter that's used as generics in the context. For example template
65 /// parameters.
67
68 /// External parameters in Objective-C methods.
69 /// For example, \c forKey in
70 /// \code{.m}
71 /// - (void) setValue:(Value)value forKey(Key)key
72 /// \endcode
74
75 /// Internal/local parameters in Objective-C methods.
76 /// For example, \c key in
77 /// \code{.m}
78 /// - (void) setValue:(Value)value forKey(Key)key
79 /// \endcode
81
82 Text,
83 };
84
85 /// Fragment holds information of a single fragment.
86 struct Fragment {
87 std::string Spelling;
89
90 /// The USR of the fragment symbol, if applicable.
91 std::string PreciseIdentifier;
92
93 /// The associated declaration, if applicable. This is not intended to be
94 /// used outside of libclang.
96
98 const Decl *Declaration)
101 };
102
103 using FragmentIterator = std::vector<Fragment>::iterator;
104 using ConstFragmentIterator = std::vector<Fragment>::const_iterator;
105
106 const std::vector<Fragment> &getFragments() const { return Fragments; }
107
108 FragmentIterator begin() { return Fragments.begin(); }
109
110 FragmentIterator end() { return Fragments.end(); }
111
112 ConstFragmentIterator cbegin() const { return Fragments.cbegin(); }
113
114 ConstFragmentIterator cend() const { return Fragments.cend(); }
115
116 // Add a new Fragment at an arbitrary offset.
118 FragmentKind Kind,
119 StringRef PreciseIdentifier = "",
120 const Decl *Declaration = nullptr) {
121 Fragments.insert(It,
122 Fragment(Spelling, Kind, PreciseIdentifier, Declaration));
123 return *this;
124 }
125
128 Fragments.insert(It, std::make_move_iterator(Other.Fragments.begin()),
129 std::make_move_iterator(Other.Fragments.end()));
130 Other.Fragments.clear();
131 return *this;
132 }
133
134 /// Append a new Fragment to the end of the Fragments.
135 ///
136 /// \returns a reference to the DeclarationFragments object itself after
137 /// appending to chain up consecutive appends.
138 DeclarationFragments &append(StringRef Spelling, FragmentKind Kind,
139 StringRef PreciseIdentifier = "",
140 const Decl *Declaration = nullptr) {
141 if (Kind == FragmentKind::Text && !Fragments.empty() &&
142 Fragments.back().Kind == FragmentKind::Text) {
143 // If appending a text fragment, and the last fragment is also text,
144 // merge into the last fragment.
145 Fragments.back().Spelling.append(Spelling.data(), Spelling.size());
146 } else {
147 Fragments.emplace_back(Spelling, Kind, PreciseIdentifier, Declaration);
148 }
149 return *this;
150 }
151
152 /// Append another DeclarationFragments to the end.
153 ///
154 /// Note: \p Other is moved from and cannot be used after a call to this
155 /// method.
156 ///
157 /// \returns a reference to the DeclarationFragments object itself after
158 /// appending to chain up consecutive appends.
160 Fragments.insert(Fragments.end(),
161 std::make_move_iterator(Other.Fragments.begin()),
162 std::make_move_iterator(Other.Fragments.end()));
163 Other.Fragments.clear();
164 return *this;
165 }
166
168 Fragments.pop_back();
169 return *this;
170 }
171
172 DeclarationFragments &replace(std::string NewSpelling, unsigned Position) {
173 Fragments.at(Position).Spelling = NewSpelling;
174 return *this;
175 }
176
177 /// Append a text Fragment of a space character.
178 ///
179 /// \returns a reference to the DeclarationFragments object itself after
180 /// appending to chain up consecutive appends.
182
183 /// Append a text Fragment of a semicolon character.
184 ///
185 /// \returns a reference to the DeclarationFragments object itself after
186 /// appending to chain up consecutive appends.
188
189 /// Removes a trailing semicolon character if present.
190 ///
191 /// \returns a reference to the DeclarationFragments object itself after
192 /// removing to chain up consecutive operations.
194
195 /// Get the string description of a FragmentKind \p Kind.
196 static StringRef getFragmentKindString(FragmentKind Kind);
197
198 /// Get the corresponding FragmentKind from string \p S.
199 static FragmentKind parseFragmentKindFromString(StringRef S);
200
203
205
206private:
207 DeclarationFragments &appendUnduplicatedTextCharacter(char Character);
208 std::vector<Fragment> Fragments;
209};
210
212public:
213 AccessControl(std::string Access) : Access(Access) {}
214 AccessControl() : Access("public") {}
215
216 const std::string &getAccess() const { return Access; }
217
218 bool empty() const { return Access.empty(); }
219
220private:
221 std::string Access;
222};
223
224/// Store function signature information with DeclarationFragments of the
225/// return type and parameters.
227public:
228 FunctionSignature() = default;
229
230 /// Parameter holds the name and DeclarationFragments of a single parameter.
231 struct Parameter {
232 std::string Name;
234
237 };
238
239 const std::vector<Parameter> &getParameters() const { return Parameters; }
240 const DeclarationFragments &getReturnType() const { return ReturnType; }
241
243 DeclarationFragments Fragments) {
244 Parameters.emplace_back(Name, Fragments);
245 return *this;
246 }
247
248 void setReturnType(DeclarationFragments RT) { ReturnType = RT; }
249
250 /// Determine if the FunctionSignature is empty.
251 ///
252 /// \returns true if the return type DeclarationFragments is empty and there
253 /// is no parameter, otherwise false.
254 bool empty() const {
255 return Parameters.empty() && ReturnType.getFragments().empty();
256 }
257
258private:
259 std::vector<Parameter> Parameters;
260 DeclarationFragments ReturnType;
261};
262
263/// A factory class to build DeclarationFragments for different kinds of Decl.
265public:
266 /// Build FunctionSignature for a function-like declaration \c FunctionT like
267 /// FunctionDecl, ObjCMethodDecl, or CXXMethodDecl.
268 ///
269 /// The logic and implementation of building a signature for a FunctionDecl,
270 /// CXXMethodDecl, and ObjCMethodDecl are exactly the same, but they do not
271 /// share a common base. This template helps reuse the code.
272 template <typename FunctionT>
273 static FunctionSignature getFunctionSignature(const FunctionT *Function);
274
276 switch (Decl->getAccess()) {
277 case AS_public:
278 case AS_none:
279 return AccessControl("public");
280 case AS_private:
281 return AccessControl("private");
282 case AS_protected:
283 return AccessControl("protected");
284 }
285 llvm_unreachable("Unhandled access control");
286 }
287
290
291 /// Build DeclarationFragments for a variable declaration VarDecl.
293
295
296 /// Build DeclarationFragments for a function declaration FunctionDecl.
298
299 /// Build DeclarationFragments for an enum constant declaration
300 /// EnumConstantDecl.
303
304 /// Build DeclarationFragments for an enum declaration EnumDecl.
306
307 /// Build DeclarationFragments for a field declaration FieldDecl.
309
310 /// Build DeclarationFragments for a struct/union record declaration
311 /// RecordDecl.
313
315
318
320
323
326
329
332 const std::optional<ArrayRef<TemplateArgumentLoc>>);
333
335
338
341
344
347
350
353
356
357 /// Build DeclarationFragments for an Objective-C category declaration
358 /// ObjCCategoryDecl.
361
362 /// Build DeclarationFragments for an Objective-C interface declaration
363 /// ObjCInterfaceDecl.
366
367 /// Build DeclarationFragments for an Objective-C method declaration
368 /// ObjCMethodDecl.
370
371 /// Build DeclarationFragments for an Objective-C property declaration
372 /// ObjCPropertyDecl.
375
376 /// Build DeclarationFragments for an Objective-C protocol declaration
377 /// ObjCProtocolDecl.
380
381 /// Build DeclarationFragments for a macro.
382 ///
383 /// \param Name name of the macro.
384 /// \param MD the associated MacroDirective.
385 static DeclarationFragments getFragmentsForMacro(StringRef Name,
386 const MacroDirective *MD);
387
388 /// Build DeclarationFragments for a typedef \p TypedefNameDecl.
391
392 /// Build sub-heading fragments for a NamedDecl.
394
395 /// Build sub-heading fragments for an Objective-C method.
397
398 /// Build a sub-heading for macro \p Name.
399 static DeclarationFragments getSubHeadingForMacro(StringRef Name);
400
401private:
403
404 /// Build DeclarationFragments for a QualType.
405 static DeclarationFragments getFragmentsForType(const QualType, ASTContext &,
407
408 /// Build DeclarationFragments for a Type.
409 static DeclarationFragments getFragmentsForType(const Type *, ASTContext &,
411
412 /// Build DeclarationFragments for a NestedNameSpecifier.
413 static DeclarationFragments getFragmentsForNNS(const NestedNameSpecifier *,
414 ASTContext &,
416
417 /// Build DeclarationFragments for Qualifiers.
418 static DeclarationFragments getFragmentsForQualifiers(const Qualifiers quals);
419
420 /// Build DeclarationFragments for a parameter variable declaration
421 /// ParmVarDecl.
422 static DeclarationFragments getFragmentsForParam(const ParmVarDecl *);
423
425 getFragmentsForBlock(const NamedDecl *BlockDecl, FunctionTypeLoc &Block,
426 FunctionProtoTypeLoc &BlockProto,
427 DeclarationFragments &After);
428};
429
430template <typename FunctionT>
431FunctionSignature
433 FunctionSignature Signature;
434
435 DeclarationFragments ReturnType, After;
436 ReturnType = getFragmentsForType(Function->getReturnType(),
437 Function->getASTContext(), After);
438 if (isa<FunctionDecl>(Function) &&
439 dyn_cast<FunctionDecl>(Function)->getDescribedFunctionTemplate() &&
440 StringRef(ReturnType.begin()->Spelling).starts_with("type-parameter")) {
441 std::string ProperArgName = Function->getReturnType().getAsString();
442 ReturnType.begin()->Spelling.swap(ProperArgName);
443 }
444 ReturnType.append(std::move(After));
445 Signature.setReturnType(ReturnType);
446
447 for (const auto *Param : Function->parameters())
448 Signature.addParameter(Param->getName(), getFragmentsForParam(Param));
449
450 return Signature;
451}
452
453} // namespace extractapi
454} // namespace clang
455
456#endif // LLVM_CLANG_EXTRACTAPI_DECLARATION_FRAGMENTS_H
Defines the clang::ASTContext interface.
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....
Defines the C++ template declaration subclasses.
Defines the clang::Expr interface and subclasses for C++ expressions.
Defines the clang::MacroInfo and clang::MacroDirective classes.
Defines various enumerations that describe declaration and type specifiers.
Defines the clang::TypeLoc interface and its subclasses.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:182
Represents a block literal declaration, which is like an unnamed FunctionDecl.
Definition: Decl.h:4495
Represents a C++ conversion function within a class.
Definition: DeclCXX.h:2859
Represents a static or instance method of a struct/union/class.
Definition: DeclCXX.h:2057
Represents a C++ struct/union/class.
Definition: DeclCXX.h:258
Represents a class template specialization, which refers to a class template with a given set of temp...
Declaration of a C++20 concept.
Decl - This represents one declaration (or definition), e.g.
Definition: DeclBase.h:85
AccessSpecifier getAccess() const
Definition: DeclBase.h:512
An instance of this object exists for each enum constant that is defined.
Definition: Decl.h:3298
Represents an enum.
Definition: Decl.h:3868
Represents a member of a struct/union/class.
Definition: Decl.h:3058
Represents a function declaration or definition.
Definition: Decl.h:1971
Declaration of a template function.
Definition: DeclTemplate.h:958
Wrapper for source info for functions.
Definition: TypeLoc.h:1428
Encapsulates changes to the "macros namespace" (the location where the macro name became active,...
Definition: MacroInfo.h:313
This represents a decl that may have a name.
Definition: Decl.h:249
Represent a C++ namespace.
Definition: Decl.h:547
Represents a C++ nested name specifier, such as "\::std::vector<int>::".
ObjCCategoryDecl - Represents a category declaration.
Definition: DeclObjC.h:2323
Represents an ObjC class declaration.
Definition: DeclObjC.h:1152
ObjCMethodDecl - Represents an instance or class method declaration.
Definition: DeclObjC.h:140
Represents one property declaration in an Objective-C interface.
Definition: DeclObjC.h:729
Represents an Objective-C protocol declaration.
Definition: DeclObjC.h:2079
Represents a parameter to a function.
Definition: Decl.h:1761
A (possibly-)qualified type.
Definition: Type.h:738
The collection of all-type qualifiers we support.
Definition: Type.h:148
Represents a struct/union/class.
Definition: Decl.h:4169
Declaration of a redeclarable template.
Definition: DeclTemplate.h:717
The base class of the type hierarchy.
Definition: Type.h:1607
Base class for declarations which introduce a typedef-name.
Definition: Decl.h:3433
Represents a variable declaration or definition.
Definition: Decl.h:918
Represents a variable template specialization, which refers to a variable template with a given set o...
const std::string & getAccess() const
A factory class to build DeclarationFragments for different kinds of Decl.
static DeclarationFragments getFragmentsForRedeclarableTemplate(const RedeclarableTemplateDecl *)
static DeclarationFragments getFragmentsForCXXClass(const CXXRecordDecl *)
static DeclarationFragments getFragmentsForEnumConstant(const EnumConstantDecl *)
Build DeclarationFragments for an enum constant declaration EnumConstantDecl.
static DeclarationFragments getFragmentsForObjCCategory(const ObjCCategoryDecl *)
Build DeclarationFragments for an Objective-C category declaration ObjCCategoryDecl.
static DeclarationFragments getFragmentsForTypedef(const TypedefNameDecl *Decl)
Build DeclarationFragments for a typedef TypedefNameDecl.
static DeclarationFragments getFragmentsForEnum(const EnumDecl *)
Build DeclarationFragments for an enum declaration EnumDecl.
static DeclarationFragments getFragmentsForConversionFunction(const CXXConversionDecl *)
static DeclarationFragments getFragmentsForClassTemplateSpecialization(const ClassTemplateSpecializationDecl *)
static DeclarationFragments getFragmentsForTemplateParameters(ArrayRef< NamedDecl * >)
static DeclarationFragments getFragmentsForObjCProtocol(const ObjCProtocolDecl *)
Build DeclarationFragments for an Objective-C protocol declaration ObjCProtocolDecl.
static DeclarationFragments getFragmentsForConcept(const ConceptDecl *)
static DeclarationFragments getFragmentsForField(const FieldDecl *)
Build DeclarationFragments for a field declaration FieldDecl.
static DeclarationFragments getFragmentsForVar(const VarDecl *)
Build DeclarationFragments for a variable declaration VarDecl.
static DeclarationFragments getFragmentsForTemplateArguments(const ArrayRef< TemplateArgument >, ASTContext &, const std::optional< ArrayRef< TemplateArgumentLoc > >)
static DeclarationFragments getFragmentsForClassTemplatePartialSpecialization(const ClassTemplatePartialSpecializationDecl *)
static DeclarationFragments getFragmentsForObjCMethod(const ObjCMethodDecl *)
Build DeclarationFragments for an Objective-C method declaration ObjCMethodDecl.
static DeclarationFragments getSubHeadingForMacro(StringRef Name)
Build a sub-heading for macro Name.
static DeclarationFragments getFragmentsForFunction(const FunctionDecl *)
Build DeclarationFragments for a function declaration FunctionDecl.
static AccessControl getAccessControl(const Decl *Decl)
static DeclarationFragments getFragmentsForObjCProperty(const ObjCPropertyDecl *)
Build DeclarationFragments for an Objective-C property declaration ObjCPropertyDecl.
static DeclarationFragments getFragmentsForSpecialCXXMethod(const CXXMethodDecl *)
static DeclarationFragments getFragmentsForCXXMethod(const CXXMethodDecl *)
static DeclarationFragments getFragmentsForNamespace(const NamespaceDecl *Decl)
static DeclarationFragments getFragmentsForVarTemplatePartialSpecialization(const VarTemplatePartialSpecializationDecl *)
static DeclarationFragments getFragmentsForFunctionTemplate(const FunctionTemplateDecl *Decl)
static DeclarationFragments getFragmentsForVarTemplateSpecialization(const VarTemplateSpecializationDecl *)
static FunctionSignature getFunctionSignature(const FunctionT *Function)
Build FunctionSignature for a function-like declaration FunctionT like FunctionDecl,...
static DeclarationFragments getSubHeading(const NamedDecl *)
Build sub-heading fragments for a NamedDecl.
static DeclarationFragments getFragmentsForVarTemplate(const VarDecl *)
static DeclarationFragments getFragmentsForOverloadedOperator(const CXXMethodDecl *)
static DeclarationFragments getFragmentsForFunctionTemplateSpecialization(const FunctionDecl *Decl)
static DeclarationFragments getFragmentsForMacro(StringRef Name, const MacroDirective *MD)
Build DeclarationFragments for a macro.
static DeclarationFragments getFragmentsForRecordDecl(const RecordDecl *)
Build DeclarationFragments for a struct/union record declaration RecordDecl.
static DeclarationFragments getFragmentsForObjCInterface(const ObjCInterfaceDecl *)
Build DeclarationFragments for an Objective-C interface declaration ObjCInterfaceDecl.
DeclarationFragments is a vector of tagged important parts of a symbol's declaration.
DeclarationFragments & replace(std::string NewSpelling, unsigned Position)
std::vector< Fragment >::iterator FragmentIterator
const std::vector< Fragment > & getFragments() const
DeclarationFragments & appendSpace()
Append a text Fragment of a space character.
DeclarationFragments & append(DeclarationFragments &&Other)
Append another DeclarationFragments to the end.
static DeclarationFragments getExceptionSpecificationString(ExceptionSpecificationType ExceptionSpec)
DeclarationFragments & insert(FragmentIterator It, StringRef Spelling, FragmentKind Kind, StringRef PreciseIdentifier="", const Decl *Declaration=nullptr)
@ GenericParameter
Parameter that's used as generics in the context.
@ ExternalParam
External parameters in Objective-C methods.
@ TypeIdentifier
Identifier that refers to a type in the context.
@ InternalParam
Internal/local parameters in Objective-C methods.
DeclarationFragments & removeTrailingSemicolon()
Removes a trailing semicolon character if present.
static StringRef getFragmentKindString(FragmentKind Kind)
Get the string description of a FragmentKind Kind.
static DeclarationFragments getStructureTypeFragment(const RecordDecl *Decl)
std::vector< Fragment >::const_iterator ConstFragmentIterator
DeclarationFragments & insert(FragmentIterator It, DeclarationFragments &&Other)
DeclarationFragments & appendSemicolon()
Append a text Fragment of a semicolon character.
static FragmentKind parseFragmentKindFromString(StringRef S)
Get the corresponding FragmentKind from string S.
DeclarationFragments & append(StringRef Spelling, FragmentKind Kind, StringRef PreciseIdentifier="", const Decl *Declaration=nullptr)
Append a new Fragment to the end of the Fragments.
Store function signature information with DeclarationFragments of the return type and parameters.
FunctionSignature & addParameter(StringRef Name, DeclarationFragments Fragments)
void setReturnType(DeclarationFragments RT)
const std::vector< Parameter > & getParameters() const
const DeclarationFragments & getReturnType() const
bool empty() const
Determine if the FunctionSignature is empty.
The JSON file list parser is used to communicate input to InstallAPI.
@ Other
Other implicit parameter.
ExceptionSpecificationType
The various types of exception specifications that exist in C++11.
@ AS_public
Definition: Specifiers.h:121
@ AS_protected
Definition: Specifiers.h:122
@ AS_none
Definition: Specifiers.h:124
@ AS_private
Definition: Specifiers.h:123
Fragment holds information of a single fragment.
std::string PreciseIdentifier
The USR of the fragment symbol, if applicable.
const Decl * Declaration
The associated declaration, if applicable.
Fragment(StringRef Spelling, FragmentKind Kind, StringRef PreciseIdentifier, const Decl *Declaration)
Parameter holds the name and DeclarationFragments of a single parameter.
Parameter(StringRef Name, DeclarationFragments Fragments)