16 #ifndef LLVM_CLANG_AST_ASTTYPETRAITS_H
17 #define LLVM_CLANG_AST_ASTTYPETRAITS_H
26 #include "llvm/ADT/DenseMapInfo.h"
27 #include "llvm/Support/AlignOf.h"
37 struct PrintingPolicy;
39 namespace ast_type_traits {
66 return KindId != NKI_None && KindId == Other.KindId;
70 bool isNone()
const {
return KindId == NKI_None; }
82 return KindId < Other.KindId;
107 return LHS.KindId == RHS.KindId;
114 return KindId > NKI_LastKindWithoutPointerIdentity;
123 NKI_TemplateArgument,
124 NKI_NestedNameSpecifierLoc,
127 NKI_LastKindWithoutPointerIdentity = NKI_TypeLoc,
128 NKI_CXXCtorInitializer,
129 NKI_NestedNameSpecifier,
131 #define DECL(DERIVED, BASE) NKI_##DERIVED##Decl,
132 #include "clang/AST/DeclNodes.inc"
134 #define STMT(DERIVED, BASE) NKI_##DERIVED,
135 #include "clang/AST/StmtNodes.inc"
137 #define TYPE(DERIVED, BASE) NKI_##DERIVED##Type,
138 #include "clang/AST/TypeNodes.def"
149 static bool isBaseOf(NodeKindId
Base, NodeKindId Derived,
unsigned *Distance);
154 template <
class T>
struct KindToKindId {
155 static const NodeKindId Id = NKI_None;
158 struct KindToKindId<const T> : KindToKindId<T> {};
167 static const KindInfo AllKindInfo[NKI_NumberOfKinds];
172 #define KIND_TO_KIND_ID(Class) \
173 template <> struct ASTNodeKind::KindToKindId<Class> { \
174 static const NodeKindId Id = NKI_##Class; \
185 #define DECL(DERIVED, BASE) KIND_TO_KIND_ID(DERIVED##Decl)
186 #include "clang/AST/DeclNodes.inc"
187 #define STMT(DERIVED, BASE) KIND_TO_KIND_ID(DERIVED)
188 #include "clang/AST/StmtNodes.inc"
189 #define TYPE(DERIVED, BASE) KIND_TO_KIND_ID(DERIVED##Type)
190 #include "clang/AST/TypeNodes.def"
191 #undef KIND_TO_KIND_ID
213 template <
typename T>
230 template <
typename T>
231 const T *
get()
const {
232 return BaseConverter<T>::get(NodeKind, Storage.buffer);
238 template <
typename T>
240 return BaseConverter<T>::getUnchecked(NodeKind, Storage.buffer);
252 ? *
reinterpret_cast<void *
const *
>(Storage.buffer)
273 if (!NodeKind.
isSame(Other.NodeKind))
274 return NodeKind < Other.NodeKind;
276 if (ASTNodeKind::getFromNodeKind<QualType>().isSame(NodeKind))
277 return getUnchecked<QualType>().getAsOpaquePtr() <
280 if (ASTNodeKind::getFromNodeKind<TypeLoc>().isSame(NodeKind)) {
281 auto TLA = getUnchecked<TypeLoc>();
283 return std::make_pair(TLA.getType().getAsOpaquePtr(),
284 TLA.getOpaqueData()) <
285 std::make_pair(TLB.getType().getAsOpaquePtr(),
286 TLB.getOpaqueData());
289 if (ASTNodeKind::getFromNodeKind<NestedNameSpecifierLoc>().isSame(
291 auto NNSLA = getUnchecked<NestedNameSpecifierLoc>();
293 return std::make_pair(NNSLA.getNestedNameSpecifier(),
294 NNSLA.getOpaqueData()) <
295 std::make_pair(NNSLB.getNestedNameSpecifier(),
296 NNSLB.getOpaqueData());
305 if (!NodeKind.
isSame(Other.NodeKind))
309 if (ASTNodeKind::getFromNodeKind<QualType>().isSame(NodeKind))
312 if (ASTNodeKind::getFromNodeKind<TypeLoc>().isSame(NodeKind))
315 if (ASTNodeKind::getFromNodeKind<NestedNameSpecifierLoc>().isSame(NodeKind))
316 return getUnchecked<NestedNameSpecifierLoc>() ==
341 if (ASTNodeKind::getFromNodeKind<TypeLoc>().isSame(Val.NodeKind)) {
343 return llvm::hash_combine(TL.getType().getAsOpaquePtr(),
347 if (ASTNodeKind::getFromNodeKind<NestedNameSpecifierLoc>().isSame(
350 return llvm::hash_combine(NNSL.getNestedNameSpecifier(),
351 NNSL.getOpaqueData());
370 template <
typename T,
typename EnablerT =
void>
struct BaseConverter;
373 template <
typename T,
typename BaseT>
struct DynCastPtrConverter {
374 static const T *
get(
ASTNodeKind NodeKind,
const char Storage[]) {
375 if (ASTNodeKind::getFromNodeKind<T>().isBaseOf(NodeKind))
379 static const T &
getUnchecked(ASTNodeKind NodeKind,
const char Storage[]) {
380 assert(ASTNodeKind::getFromNodeKind<T>().isBaseOf(NodeKind));
381 return *cast<T>(
static_cast<const BaseT *
>(
382 *
reinterpret_cast<const void *
const *
>(Storage)));
384 static DynTypedNode
create(
const BaseT &
Node) {
387 new (Result.Storage.buffer)
const void *(&Node);
393 template <
typename T>
struct PtrConverter {
394 static const T *
get(ASTNodeKind NodeKind,
const char Storage[]) {
395 if (ASTNodeKind::getFromNodeKind<T>().isSame(NodeKind))
399 static const T &
getUnchecked(ASTNodeKind NodeKind,
const char Storage[]) {
400 assert(ASTNodeKind::getFromNodeKind<T>().isSame(NodeKind));
401 return *
static_cast<const T *
>(
402 *
reinterpret_cast<const void *
const *
>(Storage));
406 Result.NodeKind = ASTNodeKind::getFromNodeKind<T>();
407 new (Result.Storage.buffer)
const void *(&Node);
413 template <
typename T>
struct ValueConverter {
414 static const T *
get(ASTNodeKind NodeKind,
const char Storage[]) {
415 if (ASTNodeKind::getFromNodeKind<T>().isSame(NodeKind))
416 return reinterpret_cast<const T *>(Storage);
419 static const T &
getUnchecked(ASTNodeKind NodeKind,
const char Storage[]) {
420 assert(ASTNodeKind::getFromNodeKind<T>().isSame(NodeKind));
421 return *
reinterpret_cast<const T *
>(Storage);
425 Result.NodeKind = ASTNodeKind::getFromNodeKind<T>();
426 new (Result.Storage.buffer) T(Node);
431 ASTNodeKind NodeKind;
441 llvm::AlignedCharArrayUnion<
const void *, TemplateArgument,
442 NestedNameSpecifierLoc, QualType,
446 template <
typename T>
447 struct DynTypedNode::BaseConverter<
448 T, typename std::enable_if<std::is_base_of<Decl, T>::value>
::type>
449 :
public DynCastPtrConverter<T, Decl> {};
451 template <
typename T>
452 struct DynTypedNode::BaseConverter<
453 T, typename std::enable_if<std::is_base_of<Stmt, T>::value>
::type>
454 :
public DynCastPtrConverter<T, Stmt> {};
456 template <
typename T>
457 struct DynTypedNode::BaseConverter<
458 T, typename std::enable_if<std::is_base_of<Type, T>::value>
::type>
459 :
public DynCastPtrConverter<T, Type> {};
462 struct DynTypedNode::BaseConverter<
466 struct DynTypedNode::BaseConverter<
470 struct DynTypedNode::BaseConverter<
474 struct DynTypedNode::BaseConverter<
476 void> :
public ValueConverter<NestedNameSpecifierLoc> {};
480 void> :
public ValueConverter<QualType> {};
483 struct DynTypedNode::BaseConverter<
484 TypeLoc, void> :
public ValueConverter<TypeLoc> {};
490 template <
typename T,
typename EnablerT>
struct DynTypedNode::BaseConverter {
491 static const T *
get(
ASTNodeKind NodeKind,
const char Storage[]) {
bool operator!=(const DynTypedNode &Other) const
A (possibly-)qualified type.
static ASTNodeKind getFromNode(const Decl &D)
Construct an identifier for the dynamic type of the node.
static ASTNodeKind getTombstoneKey()
static ASTNodeKind getEmptyKey()
The base class of the type hierarchy.
static DynTypedNode getTombstoneKey()
Describes how types, statements, expressions, and declarations should be printed. ...
bool operator<(const ASTNodeKind &Other) const
Strict weak ordering for ASTNodeKind.
Base wrapper for a particular "section" of type source info.
class LLVM_ALIGNAS(8) DependentTemplateSpecializationType const IdentifierInfo * Name
Represents a template specialization type whose template cannot be resolved, e.g. ...
A C++ nested-name-specifier augmented with source location information.
bool isNone() const
Returns true only for the default ASTNodeKind()
bool isBaseOf(ASTNodeKind Other, unsigned *Distance=nullptr) const
Returns true if this is a base kind of (or same as) Other.
ASTNodeKind()
Empty identifier. It matches nothing.
const T & getUnchecked() const
Retrieve the stored node as type T.
Forward-declares and imports various common LLVM datatypes that clang wants to use unqualified...
bool hasPointerIdentity() const
Check if the given ASTNodeKind identifies a type that offers pointer identity.
Forward declaration of all AST node types.
static unsigned getHashValue(const DynTypedNode &Val)
Hooks for using ASTNodeKind as a key in a DenseMap.
void dump(llvm::raw_ostream &OS, SourceManager &SM) const
Dumps the node to the given output stream.
Defines the clang::TypeLoc interface and its subclasses.
static ASTNodeKind getMostDerivedType(ASTNodeKind Kind1, ASTNodeKind Kind2)
Return the most derived type between Kind1 and Kind2.
The result type of a method or function.
#define KIND_TO_KIND_ID(Class)
const void * getMemoizationData() const
Returns a pointer that identifies the stored AST node.
Represents a C++ nested name specifier, such as "\::std::vector<int>::".
StringRef asStringRef() const
String representation of the kind.
ASTNodeKind getNodeKind() const
static DynTypedNode create(const T &Node)
Creates a DynTypedNode from Node.
static unsigned getHashValue(const ASTNodeKind &Val)
ast_type_traits::DynTypedNode Node
if(T->getSizeExpr()) TRY_TO(TraverseStmt(T-> getSizeExpr()))
Represents a template argument.
static ASTNodeKind getMostDerivedCommonAncestor(ASTNodeKind Kind1, ASTNodeKind Kind2)
Return the most derived common ancestor between Kind1 and Kind2.
bool isSame(ASTNodeKind Other) const
Returns true if this and Other represent the same kind.
bool operator<(const DynTypedNode &Other) const
Imposes an order on DynTypedNode.
bool operator==(const DynTypedNode &Other) const
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
std::unique_ptr< DiagnosticConsumer > create(StringRef OutputFile, DiagnosticOptions *Diags, bool MergeChildRecords=false)
Returns a DiagnosticConsumer that serializes diagnostics to a bitcode file.
Hooks for using DynTypedNode as a key in a DenseMap.
A dynamically typed AST node container.
Represents a C++ base or member initializer.
SourceRange getSourceRange() const
For nodes which represent textual entities in the source code, return their SourceRange.
static DynTypedNode getEmptyKey()
raw_ostream & operator<<(raw_ostream &OS, ASTNodeKind K)
A trivial tuple used to represent a source range.
static bool isEqual(const DynTypedNode &LHS, const DynTypedNode &RHS)
static bool isEqual(const ASTNodeKind &LHS, const ASTNodeKind &RHS)
void print(llvm::raw_ostream &OS, const PrintingPolicy &PP) const
Prints the node to the given output stream.
This class handles loading and caching of source files into memory.
static ASTNodeKind getFromNodeKind()
Construct an identifier for T.