[pypy-svn] r18762 - in pypy/dist/pypy: annotation rpython rpython/ootypesystem rpython/ootypesystem/test
arigo at codespeak.net
arigo at codespeak.net
Wed Oct 19 18:27:23 CEST 2005
Author: arigo
Date: Wed Oct 19 18:27:22 2005
New Revision: 18762
Modified:
pypy/dist/pypy/annotation/builtin.py
pypy/dist/pypy/rpython/llinterp.py
pypy/dist/pypy/rpython/ootypesystem/ootype.py
pypy/dist/pypy/rpython/ootypesystem/rbuiltin.py
pypy/dist/pypy/rpython/ootypesystem/rclass.py
pypy/dist/pypy/rpython/ootypesystem/test/test_ooclean.py
pypy/dist/pypy/rpython/rbuiltin.py
pypy/dist/pypy/rpython/rtyper.py
Log:
ootyper:
* hash(instances), with a new built-in ootype.ooidentityhash() supported
by the annotator and producing an operation with the same name.
* moved some ootype-specific code from rbuiltin.py to ootypesystem/rbuiltin.py
* quick fix in gendirectcall() that enables it to work in simple cases
Modified: pypy/dist/pypy/annotation/builtin.py
==============================================================================
--- pypy/dist/pypy/annotation/builtin.py (original)
+++ pypy/dist/pypy/annotation/builtin.py Wed Oct 19 18:27:22 2005
@@ -393,11 +393,16 @@
assert isinstance(c, SomeOOClass)
return SomeOOInstance(c.ootype)
+def ooidentityhash(i):
+ assert isinstance(i, SomeOOInstance)
+ return SomeInteger()
+
BUILTIN_ANALYZERS[ootype.instanceof] = instanceof
BUILTIN_ANALYZERS[ootype.new] = new
BUILTIN_ANALYZERS[ootype.null] = null
BUILTIN_ANALYZERS[ootype.runtimenew] = runtimenew
BUILTIN_ANALYZERS[ootype.classof] = classof
+BUILTIN_ANALYZERS[ootype.ooidentityhash] = ooidentityhash
#________________________________
# non-gc objects
Modified: pypy/dist/pypy/rpython/llinterp.py
==============================================================================
--- pypy/dist/pypy/rpython/llinterp.py (original)
+++ pypy/dist/pypy/rpython/llinterp.py Wed Oct 19 18:27:22 2005
@@ -670,6 +670,9 @@
def op_subclassof(self, class1, class2):
return ootype.subclassof(class1, class2)
+ def op_ooidentityhash(self, inst):
+ return ootype.ooidentityhash(inst)
+
# by default we route all logging messages to nothingness
# e.g. tests can then switch on logging to get more help
# for failing tests
Modified: pypy/dist/pypy/rpython/ootypesystem/ootype.py
==============================================================================
--- pypy/dist/pypy/rpython/ootypesystem/ootype.py (original)
+++ pypy/dist/pypy/rpython/ootypesystem/ootype.py Wed Oct 19 18:27:22 2005
@@ -324,4 +324,10 @@
def oodowncast(INSTANCE, instance):
assert instanceof(instance, INSTANCE)
return instance
-
+
+def ooidentityhash(inst):
+ assert isinstance(inst, _instance)
+ if inst:
+ return id(inst)
+ else:
+ return 0 # for all null instances
Modified: pypy/dist/pypy/rpython/ootypesystem/rbuiltin.py
==============================================================================
--- pypy/dist/pypy/rpython/ootypesystem/rbuiltin.py (original)
+++ pypy/dist/pypy/rpython/ootypesystem/rbuiltin.py Wed Oct 19 18:27:22 2005
@@ -1,11 +1,33 @@
+from pypy.annotation import model as annmodel
from pypy.rpython.ootypesystem import ootype
from pypy.rpython.ootypesystem import rclass
from pypy.objspace.flow.model import Constant
+def rtype_new(hop):
+ assert hop.args_s[0].is_constant()
+ vlist = hop.inputargs(ootype.Void)
+ return hop.genop('new', vlist,
+ resulttype = hop.r_result.lowleveltype)
+
+def rtype_classof(hop):
+ assert isinstance(hop.args_s[0], annmodel.SomeOOInstance)
+ return hop.genop('classof', hop.args_v,
+ resulttype = ootype.Class)
+
+def rtype_runtimenew(hop):
+ assert isinstance(hop.args_s[0], annmodel.SomeOOClass)
+ return hop.genop('runtimenew', hop.args_v,
+ resulttype = hop.r_result.lowleveltype)
+
+def rtype_ooidentityhash(hop):
+ assert isinstance(hop.args_s[0], annmodel.SomeOOInstance)
+ return hop.genop('ooidentityhash', hop.args_v,
+ resulttype = ootype.Signed)
+
def rtype_builtin_isinstance(hop):
if hop.s_result.is_constant():
- return hop.inputconst(lltype.Bool, hop.s_result.const)
+ return hop.inputconst(ootype.Bool, hop.s_result.const)
if hop.args_s[1].is_constant() and hop.args_s[1].const == list:
if hop.args_s[0].knowntype != list:
@@ -25,4 +47,8 @@
BUILTIN_TYPER = {}
+BUILTIN_TYPER[ootype.new] = rtype_new
+BUILTIN_TYPER[ootype.classof] = rtype_classof
+BUILTIN_TYPER[ootype.runtimenew] = rtype_runtimenew
+BUILTIN_TYPER[ootype.ooidentityhash] = rtype_ooidentityhash
BUILTIN_TYPER[isinstance] = rtype_builtin_isinstance
Modified: pypy/dist/pypy/rpython/ootypesystem/rclass.py
==============================================================================
--- pypy/dist/pypy/rpython/ootypesystem/rclass.py (original)
+++ pypy/dist/pypy/rpython/ootypesystem/rclass.py Wed Oct 19 18:27:22 2005
@@ -87,6 +87,12 @@
fielddefaults[mangled] = getattr(self.classdef.cls, name)
except AttributeError:
pass
+ #
+ # hash() support
+ if self.rtyper.needs_hash_support(self.classdef.cls):
+ from pypy.rpython import rint
+ allfields['_hash_cache_'] = rint.signed_repr
+ fields['_hash_cache_'] = ootype.Signed
ootype.addFields(self.lowleveltype, fields)
@@ -209,6 +215,19 @@
vinst, = hop.inputargs(self)
return hop.genop('classof', [vinst], resulttype=ootype.Class)
+ def rtype_hash(self, hop):
+ if self.classdef is None:
+ raise TyperError, "hash() not supported for this class"
+ if self.rtyper.needs_hash_support(self.classdef.cls):
+ vinst, = hop.inputargs(self)
+ return hop.gendirectcall(ll_inst_hash, vinst)
+ else:
+ return self.baserepr.rtype_hash(hop)
+
+ def rtype_id(self, hop):
+ vinst, = hop.inputargs(self)
+ return hop.genop('ooidentityhash', [vinst], resulttype=ootype.Signed)
+
def convert_const(self, value):
if value is None:
return ootype.null(self.lowleveltype)
@@ -246,12 +265,12 @@
def initialize_prebuilt_instance(self, value, result):
# then add instance attributes from this level
for mangled, (oot, default) in self.lowleveltype._allfields().items():
- name = unmangle(mangled)
if oot is ootype.Void:
llattrvalue = None
- elif name == '_hash_cache_': # hash() support
+ elif mangled == '_hash_cache_': # hash() support
llattrvalue = hash(value)
else:
+ name = unmangle(mangled)
try:
attrvalue = getattr(value, name)
except AttributeError:
@@ -294,3 +313,10 @@
def rtype_ne(rpair, hop):
v = rpair.rtype_eq(hop)
return hop.genop("bool_not", [v], resulttype=ootype.Bool)
+
+
+def ll_inst_hash(ins):
+ cached = ins._hash_cache_
+ if cached == 0:
+ cached = ins._hash_cache_ = ootype.ooidentityhash(ins)
+ return cached
Modified: pypy/dist/pypy/rpython/ootypesystem/test/test_ooclean.py
==============================================================================
--- pypy/dist/pypy/rpython/ootypesystem/test/test_ooclean.py (original)
+++ pypy/dist/pypy/rpython/ootypesystem/test/test_ooclean.py Wed Oct 19 18:27:22 2005
@@ -436,3 +436,27 @@
assert res == ~0x0100 & 0x3ff
res = interpret(f, [3], type_system='ootype')
assert res == ~0x0200 & 0x3ff
+
+def test_hash_preservation():
+ class C:
+ pass
+ class D(C):
+ pass
+ def f1():
+ d2 = D()
+ # xxx we assume that the identityhash doesn't change from
+ # one line to the next
+ current_identityhash = id(d2)
+ instance_hash = hash(d2)
+ return current_identityhash == instance_hash
+ res = interpret(f1, [], type_system='ootype')
+ assert res is True
+
+ c = C()
+ d = D()
+ def f2(): return hash(c)
+ def f3(): return hash(d)
+ res = interpret(f2, [], type_system='ootype')
+ assert res == hash(c)
+ res = interpret(f3, [], type_system='ootype')
+ assert res == hash(d)
Modified: pypy/dist/pypy/rpython/rbuiltin.py
==============================================================================
--- pypy/dist/pypy/rpython/rbuiltin.py (original)
+++ pypy/dist/pypy/rpython/rbuiltin.py Wed Oct 19 18:27:22 2005
@@ -11,7 +11,6 @@
from pypy.rpython.rbool import bool_repr
from pypy.rpython.rdict import rtype_r_dict
from pypy.tool import sourcetools
-from pypy.rpython.ootypesystem import ootype
class __extend__(annmodel.SomeBuiltin):
def rtyper_makerepr(self, rtyper):
@@ -265,22 +264,6 @@
return hop.genop('runtime_type_info', vlist,
resulttype = rptr.PtrRepr(lltype.Ptr(lltype.RuntimeTypeInfo)))
-def rtype_new(hop):
- assert hop.args_s[0].is_constant()
- vlist = hop.inputargs(lltype.Void)
- return hop.genop('new', vlist,
- resulttype = hop.r_result.lowleveltype)
-
-def rtype_classof(hop):
- assert isinstance(hop.args_s[0], annmodel.SomeOOInstance)
- return hop.genop('classof', hop.args_v,
- resulttype = ootype.Class)
-
-def rtype_runtimenew(hop):
- assert isinstance(hop.args_s[0], annmodel.SomeOOClass)
- return hop.genop('runtimenew', hop.args_v,
- resulttype = hop.r_result.lowleveltype)
-
BUILTIN_TYPER[lltype.malloc] = rtype_malloc
BUILTIN_TYPER[lltype.cast_pointer] = rtype_cast_pointer
BUILTIN_TYPER[lltype.cast_ptr_to_int] = rtype_cast_ptr_to_int
@@ -294,9 +277,6 @@
BUILTIN_TYPER[objectmodel.we_are_translated] = rtype_we_are_translated
BUILTIN_TYPER[objectmodel.hlinvoke] = rtype_hlinvoke
-BUILTIN_TYPER[ootype.new] = rtype_new
-BUILTIN_TYPER[ootype.classof] = rtype_classof
-BUILTIN_TYPER[ootype.runtimenew] = rtype_runtimenew
from pypy.rpython import extfunctable
Modified: pypy/dist/pypy/rpython/rtyper.py
==============================================================================
--- pypy/dist/pypy/rpython/rtyper.py (original)
+++ pypy/dist/pypy/rpython/rtyper.py Wed Oct 19 18:27:22 2005
@@ -775,8 +775,9 @@
# build the 'direct_call' operation
f = self.rtyper.getfunctionptr(spec_function)
c = inputconst(typeOf(f), f)
+ fobj = self.rtyper.type_system_deref(f)
return self.genop('direct_call', [c]+newargs_v,
- resulttype = typeOf(f).TO.RESULT)
+ resulttype = typeOf(fobj).RESULT)
def genexternalcall(self, fnname, args_v, resulttype=None, **flags):
if isinstance(resulttype, Repr):
More information about the Pypy-commit
mailing list