[pypy-svn] r68384 - in pypy/branch/gc-hash/pypy: rlib rpython rpython/lltypesystem rpython/memory/gctransform translator/c/test translator/cli translator/jvm

arigo at codespeak.net arigo at codespeak.net
Tue Oct 13 17:08:52 CEST 2009


Author: arigo
Date: Tue Oct 13 17:08:51 2009
New Revision: 68384

Modified:
   pypy/branch/gc-hash/pypy/rlib/objectmodel.py
   pypy/branch/gc-hash/pypy/rpython/llinterp.py
   pypy/branch/gc-hash/pypy/rpython/lltypesystem/lloperation.py
   pypy/branch/gc-hash/pypy/rpython/memory/gctransform/refcounting.py
   pypy/branch/gc-hash/pypy/rpython/memory/gctransform/transform.py
   pypy/branch/gc-hash/pypy/rpython/rbuiltin.py
   pypy/branch/gc-hash/pypy/translator/c/test/test_typed.py
   pypy/branch/gc-hash/pypy/translator/cli/opcodes.py
   pypy/branch/gc-hash/pypy/translator/jvm/opcodes.py
Log:
Rename the operation from 'identityhash' to 'gc_identityhash'.
Implement it in the refcounting GC.


Modified: pypy/branch/gc-hash/pypy/rlib/objectmodel.py
==============================================================================
--- pypy/branch/gc-hash/pypy/rlib/objectmodel.py	(original)
+++ pypy/branch/gc-hash/pypy/rlib/objectmodel.py	Tue Oct 13 17:08:51 2009
@@ -278,7 +278,7 @@
             from pypy.rpython.error import TyperError
             raise TyperError("compute_identity_hash() cannot be applied to"
                              " %r" % (vobj.concretetype,))
-        return hop.genop('identityhash', [vobj], resulttype=lltype.Signed)
+        return hop.genop('gc_identityhash', [vobj], resulttype=lltype.Signed)
 
 class Entry(ExtRegistryEntry):
     _about_ = compute_unique_id
@@ -319,7 +319,7 @@
         elif hop.rtyper.type_system.name == 'ootypesystem':
             from pypy.rpython.ootypesystem import ootype
             if isinstance(vobj.concretetype, ootype.Instance):
-                return hop.genop('identityhash', [vobj],
+                return hop.genop('gc_identityhash', [vobj],
                                  resulttype = ootype.Signed)
         from pypy.rpython.error import TyperError
         raise TyperError("current_object_addr_as_int() cannot be applied to"

Modified: pypy/branch/gc-hash/pypy/rpython/llinterp.py
==============================================================================
--- pypy/branch/gc-hash/pypy/rpython/llinterp.py	(original)
+++ pypy/branch/gc-hash/pypy/rpython/llinterp.py	Tue Oct 13 17:08:51 2009
@@ -801,9 +801,6 @@
         checkadr(adr)
         return llmemory.cast_adr_to_int(adr)
 
-    def op_identityhash(self, obj):
-        return lltype.identityhash(obj)
-
     def op_weakref_create(self, v_obj):
         def objgetter():    # special support for gcwrapper.py
             return self.getval(v_obj)
@@ -878,6 +875,9 @@
             self.setvar(v_ptr, p)
     op_gc_reload_possibly_moved.specialform = True
 
+    def op_gc_identityhash(self, obj):
+        return lltype.identityhash(obj)
+
     def op_gc_id(self, v_ptr):
         return self.heap.gc_id(v_ptr)
 

Modified: pypy/branch/gc-hash/pypy/rpython/lltypesystem/lloperation.py
==============================================================================
--- pypy/branch/gc-hash/pypy/rpython/lltypesystem/lloperation.py	(original)
+++ pypy/branch/gc-hash/pypy/rpython/lltypesystem/lloperation.py	Tue Oct 13 17:08:51 2009
@@ -378,7 +378,6 @@
     'direct_arrayitems':    LLOp(canfold=True),
     'direct_ptradd':        LLOp(canfold=True),
     'cast_opaque_ptr':      LLOp(sideeffects=False),
-    'identityhash':         LLOp(sideeffects=False),  # see rlib/objectmodel
 
     # __________ address operations __________
 
@@ -440,6 +439,8 @@
     'gc_push_alive_pyobj':  LLOp(),
     'gc_pop_alive_pyobj':   LLOp(),
     'gc_reload_possibly_moved': LLOp(),
+    # see rlib/objectmodel for gc_identityhash and gc_id
+    'gc_identityhash':      LLOp(canraise=(MemoryError,), sideeffects=False),
     'gc_id':                LLOp(canraise=(MemoryError,), sideeffects=False),
     'gc_set_max_heap_size': LLOp(),
     'gc_can_move'         : LLOp(sideeffects=False),

Modified: pypy/branch/gc-hash/pypy/rpython/memory/gctransform/refcounting.py
==============================================================================
--- pypy/branch/gc-hash/pypy/rpython/memory/gctransform/refcounting.py	(original)
+++ pypy/branch/gc-hash/pypy/rpython/memory/gctransform/refcounting.py	Tue Oct 13 17:08:51 2009
@@ -34,7 +34,8 @@
 class RefcountingGCTransformer(GCTransformer):
     malloc_zero_filled = True
 
-    HDR = lltype.Struct("header", ("refcount", lltype.Signed))
+    HDR = lltype.Struct("header", ("refcount", lltype.Signed),
+                                  ("hash", lltype.Signed))
 
     def __init__(self, translator):
         super(RefcountingGCTransformer, self).__init__(translator, inline=True)
@@ -91,6 +92,13 @@
         mh.ll_malloc_varsize_no_length = ll_malloc_varsize_no_length
         ll_malloc_varsize = mh.ll_malloc_varsize
 
+        def ll_identityhash(addr):
+            obj = llmemory.cast_adr_to_ptr(addr, HDRPTR)
+            h = obj.hash
+            if h == 0:
+                obj.hash = h = llmemory.cast_adr_to_int(addr)
+            return h
+
         if self.translator:
             self.increfptr = self.inittime_helper(
                 ll_incref, [llmemory.Address], lltype.Void)
@@ -107,6 +115,9 @@
                 ll_malloc_varsize_no_length, [lltype.Signed]*3, llmemory.Address)
             self.malloc_varsize_ptr = self.inittime_helper(
                 ll_malloc_varsize, [lltype.Signed]*4, llmemory.Address)
+            self.identityhash_ptr = self.inittime_helper(
+                ll_identityhash, [llmemory.Address], lltype.Signed,
+                inline=False)
             self.mixlevelannotator.finish()
             self.mixlevelannotator.backend_optimize()
         # cache graphs:
@@ -183,6 +194,7 @@
             if not self.gcheaderbuilder.get_header(p):
                 hdr = self.gcheaderbuilder.new_header(p)
                 hdr.refcount = sys.maxint // 2
+                hdr.hash = lltype.identityhash(p)
 
     def static_deallocation_funcptr_for_type(self, TYPE):
         if TYPE in self.static_deallocator_funcptrs:
@@ -286,4 +298,8 @@
         self.queryptr2dynamic_deallocator_funcptr[queryptr._obj] = fptr
         return fptr
 
-
+    def gct_gc_identityhash(self, hop):
+        v_obj = hop.spaceop.args[0]
+        v_adr = gen_cast(hop.llops, llmemory.Address, v_obj)
+        hop.genop("direct_call", [self.identityhash_ptr, v_adr],
+                  resultvar=hop.spaceop.result)

Modified: pypy/branch/gc-hash/pypy/rpython/memory/gctransform/transform.py
==============================================================================
--- pypy/branch/gc-hash/pypy/rpython/memory/gctransform/transform.py	(original)
+++ pypy/branch/gc-hash/pypy/rpython/memory/gctransform/transform.py	Tue Oct 13 17:08:51 2009
@@ -380,6 +380,10 @@
     def gct_zero_gc_pointers_inside(self, hop):
         pass
 
+    def gct_gc_identityhash(self, hop):
+        # must be implemented in the various GCs
+        raise NotImplementedError
+
     def gct_gc_id(self, hop):
         # this assumes a non-moving GC.  Moving GCs need to override this
         hop.rename('cast_ptr_to_int')

Modified: pypy/branch/gc-hash/pypy/rpython/rbuiltin.py
==============================================================================
--- pypy/branch/gc-hash/pypy/rpython/rbuiltin.py	(original)
+++ pypy/branch/gc-hash/pypy/rpython/rbuiltin.py	Tue Oct 13 17:08:51 2009
@@ -494,7 +494,7 @@
 
 def rtype_identity_hash(hop):
     vlist = hop.inputargs(hop.args_r[0])
-    return hop.genop('identityhash', vlist, resulttype=lltype.Signed)
+    return hop.genop('gc_identityhash', vlist, resulttype=lltype.Signed)
 
 def rtype_runtime_type_info(hop):
     assert isinstance(hop.args_r[0], rptr.PtrRepr)

Modified: pypy/branch/gc-hash/pypy/translator/c/test/test_typed.py
==============================================================================
--- pypy/branch/gc-hash/pypy/translator/c/test/test_typed.py	(original)
+++ pypy/branch/gc-hash/pypy/translator/c/test/test_typed.py	Tue Oct 13 17:08:51 2009
@@ -563,6 +563,7 @@
         assert f(255) == 255
 
     def test_hash_preservation(self):
+        from pypy.rlib.objectmodel import compute_hash
         from pypy.rlib.objectmodel import current_object_addr_as_int
         class C:
             pass
@@ -570,18 +571,24 @@
             pass
         c = C()
         d = D()
+        compute_hash(d)     # force to be cached on 'd', but not on 'c'
+        #
         def fn():
             d2 = D()
-            return hash(d2), current_object_addr_as_int(d2), hash(c), hash(d)
+            return (compute_hash(d2),
+                    current_object_addr_as_int(d2),
+                    compute_hash(c),
+                    compute_hash(d),
+                    compute_hash(("Hi", None, (7.5, 2, d))))
         
         f = self.getcompiled(fn)
-
         res = f()
 
-        # xxx this is too precise, checking the exact implementation
-        assert res[0] == ~res[1]
-        assert res[2] == hash(c)
-        assert res[3] == hash(d)
+        # xxx the next line is too precise, checking the exact implementation
+        assert res[0] == res[1]
+        assert res[2] != compute_hash(c)     # likely
+        assert res[3] == compute_hash(d)
+        assert res[4] == compute_hash(("Hi", None, (7.5, 2, d)))
 
     def test_list_basic_ops(self):
         def list_basic_ops(i, j):

Modified: pypy/branch/gc-hash/pypy/translator/cli/opcodes.py
==============================================================================
--- pypy/branch/gc-hash/pypy/translator/cli/opcodes.py	(original)
+++ pypy/branch/gc-hash/pypy/translator/cli/opcodes.py	Tue Oct 13 17:08:51 2009
@@ -58,7 +58,8 @@
     'classof':                  [PushAllArgs, 'callvirt instance class [mscorlib]System.Type object::GetType()'],
     'instanceof':               [CastTo, 'ldnull', 'cgt.un'],
     'subclassof':               [PushAllArgs, 'call bool [pypylib]pypy.runtime.Utils::SubclassOf(class [mscorlib]System.Type, class[mscorlib]System.Type)'],
-    'identityhash':             [PushAllArgs, 'call int32 [mscorlib]System.Runtime.CompilerServices.RuntimeHelpers::GetHashCode(object)'],
+    'gc_id':                    [PushAllArgs, 'call int32 [mscorlib]System.Runtime.CompilerServices.RuntimeHelpers::GetHashCode(object)'],   # XXX not implemented
+    'gc_identityhash':          [PushAllArgs, 'call int32 [mscorlib]System.Runtime.CompilerServices.RuntimeHelpers::GetHashCode(object)'],
     'oostring':                 [OOString],
     'oounicode':                [OOUnicode],
     'ooparse_int':              [PushAllArgs, 'call int32 [pypylib]pypy.runtime.Utils::OOParseInt(string, int32)'],

Modified: pypy/branch/gc-hash/pypy/translator/jvm/opcodes.py
==============================================================================
--- pypy/branch/gc-hash/pypy/translator/jvm/opcodes.py	(original)
+++ pypy/branch/gc-hash/pypy/translator/jvm/opcodes.py	Tue Oct 13 17:08:51 2009
@@ -82,7 +82,8 @@
     'instanceof':               [CastTo, StoreResult],
     'subclassof':               [PushAllArgs, jvm.SWAP, jvm.CLASSISASSIGNABLEFROM, StoreResult],
     'classof':                  [PushAllArgs, jvm.OBJECTGETCLASS, StoreResult],
-    'identityhash':             [PushAllArgs, jvm.SYSTEMIDENTITYHASH, StoreResult], 
+    'gc_id':                    [PushAllArgs, jvm.SYSTEMIDENTITYHASH, StoreResult],   # XXX not implemented
+    'gc_identityhash':          [PushAllArgs, jvm.SYSTEMIDENTITYHASH, StoreResult], 
     'oostring':                 [OOString, StoreResult],
     'oounicode':                [OOUnicode, StoreResult],
     'ooparse_float':            jvm.PYPYOOPARSEFLOAT,



More information about the Pypy-commit mailing list