[pypy-commit] pypy dynamic-specialized-tuple: (arigo, alex): remove the old hacks, and start making this case use arrayfield
alex_gaynor
noreply at buildbot.pypy.org
Wed Mar 14 23:20:00 CET 2012
Author: Alex Gaynor <alex.gaynor at gmail.com>
Branch: dynamic-specialized-tuple
Changeset: r53616:f1dc3bc0b202
Date: 2012-03-14 15:19 -0700
http://bitbucket.org/pypy/pypy/changeset/f1dc3bc0b202/
Log: (arigo, alex): remove the old hacks, and start making this case use
arrayfield
diff --git a/pypy/jit/backend/llgraph/llimpl.py b/pypy/jit/backend/llgraph/llimpl.py
--- a/pypy/jit/backend/llgraph/llimpl.py
+++ b/pypy/jit/backend/llgraph/llimpl.py
@@ -1205,14 +1205,10 @@
return lltype.cast_primitive(TYPE, x)
def cast_to_ptr(x):
- if lltype.typeOf(x) is llmemory.Address:
- return llmemory.cast_adr_to_ptr(x, llmemory.GCREF)
assert isinstance(lltype.typeOf(x), lltype.Ptr)
return lltype.cast_opaque_ptr(llmemory.GCREF, x)
def cast_from_ptr(TYPE, x):
- if TYPE is llmemory.Address:
- return llmemory.cast_ptr_to_adr(x)
return lltype.cast_opaque_ptr(TYPE, x)
def cast_to_floatstorage(x):
@@ -1464,14 +1460,8 @@
def new_getinteriorfield_gc(cast_func):
def do_getinteriorfield_gc(array, index, fieldnum):
- STRUCT, fieldname = symbolic.TokenToField[fieldnum]
- if isinstance(lltype.typeOf(array._obj.container), lltype.GcStruct):
- array = getattr(array._obj.container, fieldname)
- value = array.getitem(index)
- else:
- struct = array._obj.container.getitem(index)
- value = getattr(struct, fieldname)
- return cast_func(value)
+ struct = array._obj.container.getitem(index)
+ return cast_func(getattr(struct, fieldname))
return do_getinteriorfield_gc
do_getinteriorfield_gc_int = new_getinteriorfield_gc(cast_to_int)
@@ -1560,14 +1550,9 @@
def new_setinteriorfield_gc(cast_func):
def do_setinteriorfield_gc(array, index, fieldnum, newvalue):
STRUCT, fieldname = symbolic.TokenToField[fieldnum]
- if isinstance(lltype.typeOf(array._obj.container), lltype.GcStruct):
- array = getattr(array._obj.container, fieldname)
- FIELDTYPE = lltype.typeOf(array).OF
- array.setitem(index, cast_func(FIELDTYPE, newvalue))
- else:
- struct = array._obj.container.getitem(index)
- FIELDTYPE = getattr(STRUCT, fieldname)
- setattr(struct, fieldname, cast_func(FIELDTYPE, newvalue))
+ struct = array._obj.container.getitem(index)
+ FIELDTYPE = getattr(STRUCT, fieldname)
+ setattr(struct, fieldname, cast_func(FIELDTYPE, newvalue))
return do_setinteriorfield_gc
do_setinteriorfield_gc_int = new_setinteriorfield_gc(cast_from_int)
do_setinteriorfield_gc_float = new_setinteriorfield_gc(cast_from_floatstorage)
diff --git a/pypy/jit/backend/llgraph/runner.py b/pypy/jit/backend/llgraph/runner.py
--- a/pypy/jit/backend/llgraph/runner.py
+++ b/pypy/jit/backend/llgraph/runner.py
@@ -334,17 +334,11 @@
token = history.getkind(getattr(S, fieldname))
return self.getdescr(ofs, token[0], name=fieldname)
- def interiorfielddescrof(self, A, fieldname, force_kind=None):
+ def interiorfielddescrof(self, A, fieldname):
+ S = A.OF
width = symbolic.get_size(A)
- if isinstance(A, lltype.GcArray):
- S = A.OF
- ofs, size = symbolic.get_field_token(S, fieldname)
- token = history.getkind(getattr(S, fieldname))
- else:
- ofs, size = symbolic.get_field_token(A, fieldname)
- token = history.getkind(getattr(A, fieldname).OF)
- if force_kind is not None:
- token = force_kind
+ ofs, size = symbolic.get_field_token(S, fieldname)
+ token = history.getkind(getattr(S, fieldname))
return self.getdescr(ofs, token[0], name=fieldname, width=width)
def interiorfielddescrof_dynamic(self, offset, width, fieldsize,
@@ -394,25 +388,17 @@
return llimpl.grab_exc_value()
def arraydescrof(self, A):
+ assert A.OF != lltype.Void
+ assert isinstance(A, lltype.GcArray) or A._hints.get('nolength', False)
size = symbolic.get_size(A)
- if isinstance(A, lltype.GcStruct):
- token = 'S'
+ if isinstance(A.OF, lltype.Ptr) or isinstance(A.OF, lltype.Primitive):
+ token = history.getkind(A.OF)[0]
+ elif isinstance(A.OF, lltype.Struct):
+ token = 's'
else:
- assert A.OF != lltype.Void
- assert isinstance(A, lltype.GcArray) or A._hints.get('nolength', False)
- if isinstance(A.OF, lltype.Ptr) or isinstance(A.OF, lltype.Primitive):
- token = history.getkind(A.OF)[0]
- elif isinstance(A.OF, lltype.Struct):
- token = 's'
- else:
- token = '?'
+ token = '?'
return self.getdescr(size, token)
- def copy_and_change_descr_typeinfo_to_ptr(self, descr):
- return self.getdescr(descr.ofs, "r", descr.extrainfo, descr.name,
- descr.arg_types, descr.count_fields_if_immut,
- descr.ffi_flags, descr.width)
-
# ---------- the backend-dependent operations ----------
def bh_strlen(self, string):
diff --git a/pypy/jit/codewriter/jtransform.py b/pypy/jit/codewriter/jtransform.py
--- a/pypy/jit/codewriter/jtransform.py
+++ b/pypy/jit/codewriter/jtransform.py
@@ -233,12 +233,13 @@
def rewrite_op_cast_adr_to_ptr(self, op):
# HACK
prev_op = self._newoperations.pop()
- if prev_op.opname != 'getinteriorfield_gc_i':
+ if prev_op.opname != 'getarrayitem_gc_i':
raise Exception("Must cast_adr_to_ptr of directly read adr")
- prev_op.opname = 'getinteriorfield_gc_r'
+ prev_op.opname = 'getarrayitem_gc_r'
prev_op.result = op.result
- descr = self.cpu.copy_and_change_descr_typeinfo_to_ptr(prev_op.args[2])
- prev_op.args = prev_op.args[:2] + [descr]
+ prev_descr = prev_op.args[1]
+ descr = self.cpu.copy_and_change_descr_typeinfo_to_ptr(prev_descr)
+ prev_op.args = [prev_op.args[0]] + [descr] + prev_op.args[2:]
return prev_op
def rewrite_op_cast_bool_to_int(self, op): pass
@@ -812,21 +813,33 @@
opname = "unicodegetitem"
return SpaceOperation(opname, [op.args[0], op.args[2]], op.result)
else:
+ v_inst = op.args[0]
+ parts_v = op.args[1:]
if op.result.concretetype is lltype.Void:
return
- v_inst = op.args[0]
+ kind = getkind(op.result.concretetype)[0]
+ if isinstance(v_inst.concretetype.TO, lltype.GcArray):
+ # only GcArray of Struct supported
+ STRUCT = v_inst.concretetype.TO.OF
+ assert isinstance(STRUCT, lltype.Struct)
- if isinstance(v_inst.concretetype.TO, lltype.GcArray):
- v_inst, v_index, c_field = op.args
+ v_index, c_field = parts_v
+ descr = self.cpu.interiorfielddescrof(v_inst.concretetype.TO,
+ c_field.value)
+ args = [v_inst, v_index, descr]
+ return SpaceOperation('getinteriorfield_gc_%s' % kind, args,
+ op.result)
+ elif isinstance(v_inst.concretetype.TO, lltype.GcStruct):
+ # Supports the case of a GcStruct which contains an inlined
+ # array of simple types.
+ c_field, v_index = parts_v
+ assert v_inst.concretetype.TO._arrayfld == c_field.value
+ descr = self.cpu.arraydescrof(v_inst.concretetype.TO)
+ args = [v_inst, descr, v_index]
+ return SpaceOperation('getarrayitem_gc_%s' % kind, args,
+ op.result)
else:
- v_inst, c_field, v_index = op.args
-
- descr = self.cpu.interiorfielddescrof(v_inst.concretetype.TO,
- c_field.value)
- args = [v_inst, v_index, descr]
- kind = getkind(op.result.concretetype)[0]
- return SpaceOperation('getinteriorfield_gc_%s' % kind, args,
- op.result)
+ raise Exception
def rewrite_op_setinteriorfield(self, op):
assert len(op.args) == 4
@@ -840,35 +853,44 @@
return SpaceOperation(opname, [op.args[0], op.args[2], op.args[3]],
op.result)
else:
- orig_value = None
- orig_result = None
- prev_op = None
- if self._newoperations and self._newoperations[-1].opname == "cast_ptr_to_adr":
- prev_op = self._newoperations.pop()
- [orig_value] = prev_op.args
- orig_result = prev_op.result
-
v_inst = op.args[0]
- v_value = op.args[3]
+ v_value = op.args[-1]
+ parts_v = op.args[1:-1]
if v_value.concretetype is lltype.Void:
return
+
if isinstance(v_inst.concretetype.TO, lltype.GcArray):
- v_inst, v_index, c_field, v_value = op.args
+ # only GcArray of Struct supported
+ STRUCT = v_inst.concretetype.TO.OF
+ assert isinstance(STRUCT, lltype.Struct)
+
+ v_index, c_field = parts_v
+ descr = self.cpu.interiorfielddescrof(v_inst.concretetype.TO,
+ c_field.value)
+ args = [v_inst, v_index, v_value, descr]
+ kind = getkind(v_value.concretetype)[0]
+ return SpaceOperation('setinteriorfield_gc_%s' % kind, args,
+ op.result)
+ elif isinstance(v_inst.concretetype.TO, lltype.GcStruct):
+ # Supports the case of a GcStruct which contains an inlined
+ # array of simple types.
+ c_field, v_index = parts_v
+ assert v_inst.concretetype.TO._arrayfld == c_field.value
+
+ descr = self.cpu.arraydescrof(v_inst.concretetype.TO)
+
+ if self._newoperations and self._newoperations[-1].opname == "cast_ptr_to_adr":
+ prev_op = self._newoperations.pop()
+ assert v_value is prev_op.result
+ descr = self.cpu.copy_and_change_descr_typeinfo_to_ptr(descr)
+ v_value = prev_op.args[0]
+
+ args = [v_inst, descr, v_index, v_value]
+ kind = getkind(v_value.concretetype)[0]
+ return SpaceOperation('setarrayitem_gc_%s' % kind, args,
+ op.result)
else:
- v_inst, c_field, v_index, v_value = op.args
-
- assert orig_result is None or orig_result is v_value
- if orig_value is not None:
- v_value = orig_value
-
- descr = self.cpu.interiorfielddescrof(v_inst.concretetype.TO,
- c_field.value)
- if prev_op is not None:
- descr = self.cpu.copy_and_change_descr_typeinfo_to_ptr(descr)
- kind = getkind(v_value.concretetype)[0]
- args = [v_inst, v_index, v_value, descr]
- return SpaceOperation('setinteriorfield_gc_%s' % kind, args,
- op.result)
+ raise Exception("Obscure")
def _rewrite_equality(self, op, opname):
arg0, arg1 = op.args
diff --git a/pypy/jit/codewriter/test/test_jtransform.py b/pypy/jit/codewriter/test/test_jtransform.py
--- a/pypy/jit/codewriter/test/test_jtransform.py
+++ b/pypy/jit/codewriter/test/test_jtransform.py
@@ -1234,7 +1234,7 @@
except Exception, e:
assert 'foobar' in str(e)
-def test_interiorfield_struct():
+def test_arrayitem_struct():
S = lltype.GcStruct("S",
("x", lltype.Signed),
("data", lltype.Array(lltype.Signed)),
@@ -1245,16 +1245,15 @@
[v, c_data, const(0), const(1)], varoftype(lltype.Void)
)
op1 = Transformer(FakeCPU()).rewrite_operation(op)
- assert op1.opname == "setinteriorfield_gc_i"
- assert op1.args == [v, const(0), const(1), ('interiorfielddescr', S, "data")]
-
+ assert op1.opname == "setarrayitem_gc_i"
+ assert op1.args == [v, ('arraydescr', S), const(0), const(1)]
op = SpaceOperation("getinteriorfield",
[v, c_data, const(0)], varoftype(lltype.Signed)
)
op1 = Transformer(FakeCPU()).rewrite_operation(op)
- assert op1.opname == "getinteriorfield_gc_i"
- assert op1.args == [v, const(0), ('interiorfielddescr', S, "data")]
+ assert op1.opname == "getarrayitem_gc_i"
+ assert op1.args == [v, ('arraydescr', S), const(0)]
def test_cast_adr_to_ptr():
S = lltype.GcStruct("S",
@@ -1274,8 +1273,8 @@
Transformer(FakeCPU()).optimize_block(block)
[op1] = block.operations
- assert op1.opname == "getinteriorfield_gc_r"
- assert op1.args == [v0, const(0), (('interiorfielddescr', S, 'data'), "r")]
+ assert op1.opname == "getarrayitem_gc_r"
+ assert op1.args == [v0, (('arraydescr', S,), "r"), const(0)]
assert op1.result == v2
def test_cast_ptr_to_adr():
@@ -1297,5 +1296,5 @@
Transformer(FakeCPU()).optimize_block(block)
[op1] = block.operations
- assert op1.opname == "setinteriorfield_gc_r"
- assert op1.args == [v0, const(0), v1, (('interiorfielddescr', S, 'data'), "r")]
+ assert op1.opname == "setarrayitem_gc_r"
+ assert op1.args == [v0, (('arraydescr', S), "r"), const(0), v1]
More information about the pypy-commit
mailing list