]> granicus.if.org Git - clang/commitdiff
Introduce the GlobalSelector class in the Indexing library.
authorArgyrios Kyrtzidis <akyrtzi@gmail.com>
Wed, 29 Jul 2009 23:40:32 +0000 (23:40 +0000)
committerArgyrios Kyrtzidis <akyrtzi@gmail.com>
Wed, 29 Jul 2009 23:40:32 +0000 (23:40 +0000)
GlobalSelector is an ASTContext-independent way to refer to Objective C selectors.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@77538 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/Index/GlobalSelector.h [new file with mode: 0644]
include/clang/Index/Program.h
lib/Index/GlobalSelector.cpp [new file with mode: 0644]
lib/Index/ProgramImpl.h

diff --git a/include/clang/Index/GlobalSelector.h b/include/clang/Index/GlobalSelector.h
new file mode 100644 (file)
index 0000000..7bbd303
--- /dev/null
@@ -0,0 +1,95 @@
+//===--- GlobalSelector.h - Cross-translation-unit "token" for selectors --===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+//  GlobalSelector is a ASTContext-independent way to refer to selectors.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_INDEX_GLOBALSELECTOR_H
+#define LLVM_CLANG_INDEX_GLOBALSELECTOR_H
+
+#include "llvm/ADT/DenseMap.h"
+#include <string>
+
+namespace clang {
+  class ASTContext;
+  class Selector;
+
+namespace idx {
+  class Program;
+
+/// \brief A ASTContext-independent way to refer to selectors.
+class GlobalSelector {
+  void *Val;
+
+  explicit GlobalSelector(void *val) : Val(val) { }
+
+public:
+  GlobalSelector() : Val(0) { }
+
+  /// \brief Get the ASTContext-specific selector.
+  Selector getSelector(ASTContext &AST) const;
+
+  bool isValid() const { return Val != 0; }
+  bool isInvalid() const { return !isValid(); }
+
+  /// \brief Get a printable name for debugging purpose.
+  std::string getPrintableName() const;
+
+  /// \brief Get a GlobalSelector for the ASTContext-specific selector.
+  static GlobalSelector get(Selector Sel, Program &Prog);
+  
+  void *getAsOpaquePtr() const { return Val; }
+
+  friend bool operator==(const GlobalSelector &LHS, const GlobalSelector &RHS) { 
+    return LHS.getAsOpaquePtr() == RHS.getAsOpaquePtr();
+  }
+  
+  // For use in a std::map.
+  friend bool operator< (const GlobalSelector &LHS, const GlobalSelector &RHS) { 
+    return LHS.getAsOpaquePtr() < RHS.getAsOpaquePtr();
+  }
+
+  // For use in DenseMap/DenseSet.
+  static GlobalSelector getEmptyMarker() { return GlobalSelector((void*)-1); }
+  static GlobalSelector getTombstoneMarker() {
+    return GlobalSelector((void*)-2);
+  }
+};
+  
+} // namespace idx
+
+} // namespace clang
+
+namespace llvm {
+/// Define DenseMapInfo so that GlobalSelectors can be used as keys in DenseMap
+/// and DenseSets.
+template<>
+struct DenseMapInfo<clang::idx::GlobalSelector> {
+  static inline clang::idx::GlobalSelector getEmptyKey() {
+    return clang::idx::GlobalSelector::getEmptyMarker();
+  }
+
+  static inline clang::idx::GlobalSelector getTombstoneKey() {
+    return clang::idx::GlobalSelector::getTombstoneMarker();
+  }
+
+  static unsigned getHashValue(clang::idx::GlobalSelector);
+
+  static inline bool 
+  isEqual(clang::idx::GlobalSelector LHS, clang::idx::GlobalSelector RHS) {
+    return LHS == RHS;
+  }
+
+  static inline bool isPod() { return true; }
+};
+
+}  // end namespace llvm
+
+#endif
index b2bdaa6c2e24e9583bcab0a3efe1bb2df984bbf9..a9e0b878d7767a676c77c91714b982909ce1975a 100644 (file)
@@ -28,6 +28,7 @@ class Program {
   Program(const Program&); // do not implement
   Program &operator=(const Program &); // do not implement
   friend class Entity;
+  friend class GlobalSelector;
   
 public:
   Program();
diff --git a/lib/Index/GlobalSelector.cpp b/lib/Index/GlobalSelector.cpp
new file mode 100644 (file)
index 0000000..9b18741
--- /dev/null
@@ -0,0 +1,72 @@
+//===-- GlobalSelector.cpp - Cross-translation-unit "token" for selectors -===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+//  GlobalSelector is a ASTContext-independent way to refer to selectors.
+//
+//===----------------------------------------------------------------------===//
+
+#include "clang/Index/GlobalSelector.h"
+#include "ProgramImpl.h"
+#include "clang/Index/Program.h"
+#include "clang/AST/ASTContext.h"
+using namespace clang;
+using namespace idx;
+
+/// \brief Get the ASTContext-specific selector.
+Selector GlobalSelector::getSelector(ASTContext &AST) const {
+  if (isInvalid())
+    return Selector();
+
+  Selector GlobSel = Selector(reinterpret_cast<uintptr_t>(Val));
+
+  llvm::SmallVector<IdentifierInfo *, 8> Ids;
+  for (unsigned i = 0, e = GlobSel.isUnarySelector() ? 1 : GlobSel.getNumArgs();
+         i != e; ++i) {
+    IdentifierInfo *GlobII = GlobSel.getIdentifierInfoForSlot(i);
+    IdentifierInfo *II = &AST.Idents.get(GlobII->getName(),
+                                       GlobII->getName() + GlobII->getLength());
+    Ids.push_back(II);
+  }
+
+  return AST.Selectors.getSelector(Ids.size(), Ids.data());
+}
+
+/// \brief Get a printable name for debugging purpose.
+std::string GlobalSelector::getPrintableName() const {
+  if (isInvalid())
+    return "<< Invalid >>";
+  
+  Selector GlobSel = Selector(reinterpret_cast<uintptr_t>(Val));
+  return GlobSel.getAsString();
+}
+
+/// \brief Get a GlobalSelector for the ASTContext-specific selector.
+GlobalSelector GlobalSelector::get(Selector Sel, Program &Prog) {
+  if (Sel.isNull())
+    return GlobalSelector();
+
+  ProgramImpl &ProgImpl = *static_cast<ProgramImpl*>(Prog.Impl);
+
+  llvm::SmallVector<IdentifierInfo *, 8> Ids;
+  for (unsigned i = 0, e = Sel.isUnarySelector() ? 1 : Sel.getNumArgs();
+         i != e; ++i) {
+    IdentifierInfo *II = Sel.getIdentifierInfoForSlot(i);
+    IdentifierInfo *GlobII = &ProgImpl.getIdents().get(II->getName(),
+                                               II->getName() + II->getLength());
+    Ids.push_back(GlobII);
+  }
+
+  Selector GlobSel = ProgImpl.getSelectors().getSelector(Ids.size(),Ids.data());
+  return GlobalSelector(GlobSel.getAsOpaquePtr());
+}
+
+unsigned 
+llvm::DenseMapInfo<GlobalSelector>::getHashValue(GlobalSelector Sel) {
+  return DenseMapInfo<void*>::getHashValue(Sel.getAsOpaquePtr());
+}
index b962a2d3275434628da20f18871846eb5e1b2da6..1fbff9b325606db333d3e9f98657fc4a227cde43 100644 (file)
@@ -32,6 +32,7 @@ private:
   llvm::BumpPtrAllocator BumpAlloc;
   
   IdentifierTable Identifiers;
+  SelectorTable Selectors;
 
   ProgramImpl(const ProgramImpl&); // do not implement
   ProgramImpl &operator=(const ProgramImpl &); // do not implement
@@ -41,6 +42,7 @@ public:
   
   EntitySetTy &getEntities() { return Entities; }
   IdentifierTable &getIdents() { return Identifiers; }
+  SelectorTable &getSelectors() { return Selectors; }
 
   void *Allocate(unsigned Size, unsigned Align = 8) {
     return BumpAlloc.Allocate(Size, Align);