1 //===--- Entity.h - Cross-translation-unit "token" for decls ----*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 // Entity is a ASTContext-independent way to refer to declarations that are
11 // visible across translation units.
13 //===----------------------------------------------------------------------===//
15 #ifndef LLVM_CLANG_INDEX_ENTITY_H
16 #define LLVM_CLANG_INDEX_ENTITY_H
18 #include "clang/Basic/LLVM.h"
19 #include "llvm/ADT/PointerUnion.h"
20 #include "llvm/ADT/DenseMap.h"
21 #include "llvm/ADT/StringRef.h"
32 /// \brief A ASTContext-independent way to refer to declarations.
34 /// Entity is basically the link for declarations that are semantically the same
35 /// in multiple ASTContexts. A client will convert a Decl into an Entity and
36 /// later use that Entity to find the "same" Decl into another ASTContext.
37 /// Declarations that are semantically the same and visible across translation
38 /// units will be associated with the same Entity.
40 /// An Entity may also refer to declarations that cannot be visible across
41 /// translation units, e.g. static functions with the same name in multiple
42 /// translation units will be associated with different Entities.
44 /// Entities can be checked for equality but note that the same Program object
45 /// should be used when getting Entities.
48 /// \brief Stores the Decl directly if it is not visible outside of its own
49 /// translation unit, otherwise it stores the associated EntityImpl.
50 llvm::PointerUnion<Decl *, EntityImpl *> Val;
52 explicit Entity(Decl *D);
53 explicit Entity(EntityImpl *impl) : Val(impl) { }
54 friend class EntityGetter;
59 /// \brief Find the Decl that can be referred to by this entity.
60 Decl *getDecl(ASTContext &AST) const;
62 /// \brief If this Entity represents a declaration that is internal to its
63 /// translation unit, getInternalDecl() returns it.
64 Decl *getInternalDecl() const {
65 assert(isInternalToTU() && "This Entity is not internal!");
66 return Val.get<Decl *>();
69 /// \brief Get a printable name for debugging purpose.
70 std::string getPrintableName() const;
72 /// \brief Get an Entity associated with the given Decl.
73 /// \returns invalid Entity if an Entity cannot refer to this Decl.
74 static Entity get(Decl *D, Program &Prog);
76 /// \brief Get an Entity associated with a name in the global namespace.
77 static Entity get(StringRef Name, Program &Prog);
79 /// \brief true if the Entity is not visible outside the trasnlation unit.
80 bool isInternalToTU() const {
81 assert(isValid() && "This Entity is not valid!");
82 return Val.is<Decl *>();
85 bool isValid() const { return !Val.isNull(); }
86 bool isInvalid() const { return !isValid(); }
88 void *getAsOpaquePtr() const { return Val.getOpaqueValue(); }
89 static Entity getFromOpaquePtr(void *Ptr) {
91 Ent.Val = llvm::PointerUnion<Decl *, EntityImpl *>::getFromOpaqueValue(Ptr);
95 friend bool operator==(const Entity &LHS, const Entity &RHS) {
96 return LHS.getAsOpaquePtr() == RHS.getAsOpaquePtr();
99 // For use in a std::map.
100 friend bool operator < (const Entity &LHS, const Entity &RHS) {
101 return LHS.getAsOpaquePtr() < RHS.getAsOpaquePtr();
104 // For use in DenseMap/DenseSet.
105 static Entity getEmptyMarker() {
108 llvm::PointerUnion<Decl *, EntityImpl *>::getFromOpaqueValue((void*)-1);
111 static Entity getTombstoneMarker() {
114 llvm::PointerUnion<Decl *, EntityImpl *>::getFromOpaqueValue((void*)-2);
124 /// Define DenseMapInfo so that Entities can be used as keys in DenseMap and
127 struct DenseMapInfo<clang::idx::Entity> {
128 static inline clang::idx::Entity getEmptyKey() {
129 return clang::idx::Entity::getEmptyMarker();
132 static inline clang::idx::Entity getTombstoneKey() {
133 return clang::idx::Entity::getTombstoneMarker();
136 static unsigned getHashValue(clang::idx::Entity);
139 isEqual(clang::idx::Entity LHS, clang::idx::Entity RHS) {
145 struct isPodLike<clang::idx::Entity> { static const bool value = true; };
147 } // end namespace llvm