[cfe-commits] r52653 - /cfe/trunk/lib/Analysis/CFRefCount.cpp

Ted Kremenek kremenek at apple.com
Mon Jun 23 16:30:29 PDT 2008


Author: kremenek
Date: Mon Jun 23 18:30:29 2008
New Revision: 52653

URL: http://llvm.org/viewvc/llvm-project?rev=52653&view=rev
Log:
Added ObjCSummaryCache, a new summary cache object to cache summaries for Objective-C methods.  Instead of mapping from Selectors -> Summaries, we will now map from (ObjCInterfaceDecl*,Selectors) -> Summaries.  This will allow more nuanced summary generation.  This patch just swaps in the new data structure; the rest of the code works as before by allowing the ObjCInterfaceDecl* to be null.

Modified:
    cfe/trunk/lib/Analysis/CFRefCount.cpp

Modified: cfe/trunk/lib/Analysis/CFRefCount.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Analysis/CFRefCount.cpp?rev=52653&r1=52652&r2=52653&view=diff

==============================================================================
--- cfe/trunk/lib/Analysis/CFRefCount.cpp (original)
+++ cfe/trunk/lib/Analysis/CFRefCount.cpp Mon Jun 23 18:30:29 2008
@@ -214,8 +214,52 @@
     Profile(ID, Args, Ret, DefaultArgEffect, Receiver);
   }
 };
+} // end anonymous namespace
 
+namespace {
+  class VISIBILITY_HIDDEN ObjCSummaryKey {
+    ObjCInterfaceDecl* D;
+    Selector S;
+  public:    
+    ObjCSummaryKey(ObjCInterfaceDecl* d, Selector s) : D(d), S(s) {}
+    
+    ObjCInterfaceDecl* getDecl() const { return D; }
+    Selector getSelector() const { return S; }
+  };
+}
+
+namespace llvm {
+  template <> struct DenseMapInfo<ObjCSummaryKey> {
+    static inline ObjCSummaryKey getEmptyKey() {
+      return ObjCSummaryKey(DenseMapInfo<ObjCInterfaceDecl*>::getEmptyKey(),
+                            DenseMapInfo<Selector>::getEmptyKey());
+    }
+      
+    static inline ObjCSummaryKey getTombstoneKey() {
+      return ObjCSummaryKey(DenseMapInfo<ObjCInterfaceDecl*>::getTombstoneKey(),
+                            DenseMapInfo<Selector>::getTombstoneKey());      
+    }
+    
+    static unsigned getHashValue(const ObjCSummaryKey &V) {
+      return 
+        (DenseMapInfo<ObjCInterfaceDecl*>::getHashValue(V.getDecl())&0x88888888)
+        |(DenseMapInfo<Selector>::getHashValue(V.getSelector()) & 0x55555555);
+    }
+    
+    static bool isEqual(const ObjCSummaryKey& LHS, const ObjCSummaryKey& RHS) {
+      return
+        DenseMapInfo<ObjCInterfaceDecl*>::isEqual(LHS.getDecl(), RHS.getDecl())
+        && DenseMapInfo<Selector>::isEqual(LHS.getSelector(),RHS.getSelector());
+    }
+    
+    static bool isPod() {
+      return DenseMapInfo<ObjCInterfaceDecl*>::isPod() &&
+             DenseMapInfo<Selector>::isPod();
+    }
+  };
+} // end llvm namespace
   
+namespace {
 class RetainSummaryManager {
 
   //==-----------------------------------------------------------------==//
@@ -231,8 +275,65 @@
   typedef llvm::DenseMap<FunctionDecl*, RetainSummary*>
           FuncSummariesTy;
   
+  class ObjCSummaryCache {
+    typedef llvm::DenseMap<ObjCSummaryKey, RetainSummary*> MapTy;
+    MapTy M;
+  public:
+    ObjCSummaryCache() {}
+    
+    typedef MapTy::iterator iterator;
+    
+    iterator find(ObjCInterfaceDecl* D, Selector S) {
+
+      // Do a lookup with the (D,S) pair.  If we find a match return
+      // the iterator.
+      ObjCSummaryKey K(D, S);
+      MapTy::iterator I = M.find(K);
+
+      if (I != M.end() || !D)
+        return I;
+      
+      // Walk the super chain.  If we find a hit with a parent, we'll end
+      // up returning that summary.  We actually allow that key (null,S), as
+      // we cache summaries for the null ObjCInterfaceDecl* to allow us to
+      // generate initial summaries without having to worry about NSObject
+      // being declared.
+      // FIXME: We may change this at some point.
+      for (ObjCInterfaceDecl* C=D->getSuperClass() ;; C=C->getSuperClass()) {
+        if ((I = M.find(ObjCSummaryKey(C, S))) != M.end())
+          break;
+      
+        if (!C)
+          return I;
+      }
+      
+      // Cache the summary with original key to make the next lookup faster 
+      // and return the iterator.
+      M[K] = I->second;
+      return I;
+    }
+    
+    iterator find(Selector S) {
+      return find(0, S);
+    }
+    
+    iterator end() { return M.end(); }
+    
+    RetainSummary*& operator()(ObjCInterfaceDecl* D, Selector S) {
+      return M[ ObjCSummaryKey(D,S) ];
+    }
+    
+    RetainSummary*& operator[](Selector S) {
+      return M[ ObjCSummaryKey(0,S) ];
+    }    
+  };
+  
+#if 0
   typedef llvm::DenseMap<Selector, RetainSummary*>
           ObjCMethodSummariesTy;
+#else
+  typedef ObjCSummaryCache ObjCMethodSummariesTy;
+#endif
     
   //==-----------------------------------------------------------------==//
   //  Data.





More information about the cfe-commits mailing list