[pypy-svn] r62827 - in pypy/branch/speedup-globals/pypy: interpreter objspace/std

cfbolz at codespeak.net cfbolz at codespeak.net
Tue Mar 10 19:07:12 CET 2009


Author: cfbolz
Date: Tue Mar 10 19:07:12 2009
New Revision: 62827

Modified:
   pypy/branch/speedup-globals/pypy/interpreter/pycode.py
   pypy/branch/speedup-globals/pypy/objspace/std/celldict.py
Log:
It turns out that using one additional dict lookup per call negates many of the
benefits of this optimization. Therefore, attach the cache to the code object
directly.


Modified: pypy/branch/speedup-globals/pypy/interpreter/pycode.py
==============================================================================
--- pypy/branch/speedup-globals/pypy/interpreter/pycode.py	(original)
+++ pypy/branch/speedup-globals/pypy/interpreter/pycode.py	Tue Mar 10 19:07:12 2009
@@ -111,6 +111,10 @@
 
         self._compute_flatcall()
 
+        if space.config.objspace.std.withcelldict:
+            from pypy.objspace.std.celldict import init_code
+            init_code(self)
+
     co_names = property(lambda self: [self.space.unwrap(w_name) for w_name in self.co_names_w]) # for trace
 
     def signature(self):

Modified: pypy/branch/speedup-globals/pypy/objspace/std/celldict.py
==============================================================================
--- pypy/branch/speedup-globals/pypy/objspace/std/celldict.py	(original)
+++ pypy/branch/speedup-globals/pypy/objspace/std/celldict.py	Tue Mar 10 19:07:12 2009
@@ -167,44 +167,46 @@
 class State(object):
     def __init__(self, space):
         self.space = space
-        self.code_to_index = {}
-        self.caches = []
-        self.dictimpls = []
         self.invalidcell = ModuleCell(valid=False)
         self.always_invalid_cache = []
+        self.neverused_dictimpl = ModuleDictImplementation(space)
 
-    def getcache(self, code, w_globals):
+class GlobalCacheHolder(object):
+    def __init__(self, space):
+        self.cache = None
+        state = space.fromcache(State)
+        self.dictimpl = state.neverused_dictimpl
+
+    def getcache(self, space, code, w_globals):
         implementation = getimplementation(w_globals)
-        index = -1 # for flow space
-        if code in self.code_to_index:
-            index = self.code_to_index[code]
-            if self.dictimpls[index] is implementation:
-                return self.caches[index]
-            in_dict = True
-        else:
-            in_dict = False
+        if self.dictimpl is implementation:
+            return self.cache
+        return self.getcache_slow(space, code, w_globals, implementation)
+    getcache._always_inline_ = True
+
+    def getcache_slow(self, space, code, w_globals, implementation):
+        state = space.fromcache(State)
         if not isinstance(implementation, ModuleDictImplementation):
-            missing_length = max(len(code.co_names_w) - len(self.always_invalid_cache), 0)
-            self.always_invalid_cache.extend([self.invalidcell] * missing_length)
-            return self.always_invalid_cache
-        if not in_dict:
-            index = len(self.code_to_index)
-            self.code_to_index[code] = index
-            self.dictimpls.append(None)
-            self.caches.append(None)
-        cache = [self.invalidcell] * len(code.co_names_w)
-        self.caches[index] = cache
-        self.dictimpls[index] = implementation
+            missing_length = max(len(code.co_names_w) - len(state.always_invalid_cache), 0)
+            state.always_invalid_cache.extend([state.invalidcell] * missing_length)
+            cache = state.always_invalid_cache
+        else:
+            cache = [state.invalidcell] * len(code.co_names_w)
+        self.cache = cache
+        self.dictimpl = implementation
         return cache
+    getcache_slow._dont_inline_ = True
 
+def init_code(code):
+    code.globalcacheholder = GlobalCacheHolder(code.space)
 
 
 def get_global_cache(space, code, w_globals):
     from pypy.interpreter.pycode import PyCode
     if not isinstance(code, PyCode):
         return []
-    cache = space.fromcache(State).getcache(code, w_globals)
-    return cache
+    holder = code.globalcacheholder
+    return holder.getcache(space, code, w_globals)
 
 def getimplementation(w_dict):
     if type(w_dict) is W_DictMultiObject:



More information about the Pypy-commit mailing list