[pypy-svn] r22859 - in pypy/dist/pypy/rpython/memory: . test
mwh at codespeak.net
mwh at codespeak.net
Sun Jan 29 19:47:17 CET 2006
Author: mwh
Date: Sun Jan 29 19:47:15 2006
New Revision: 22859
Modified:
pypy/dist/pypy/rpython/memory/gctransform.py
pypy/dist/pypy/rpython/memory/test/test_gctransform.py
Log:
some very nearly insane code to generate the graph of the deallocator
for an lltype.
Modified: pypy/dist/pypy/rpython/memory/gctransform.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/gctransform.py (original)
+++ pypy/dist/pypy/rpython/memory/gctransform.py Sun Jan 29 19:47:15 2006
@@ -1,5 +1,6 @@
from pypy.rpython.lltypesystem import lltype
-from pypy.objspace.flow.model import SpaceOperation, Variable, Constant, c_last_exception
+from pypy.objspace.flow.model import SpaceOperation, Variable, Constant, \
+ c_last_exception, FunctionGraph, Block, Link, checkgraph
from pypy.translator.unsimplify import insert_empty_block
from pypy.rpython import rmodel
import sets
@@ -168,3 +169,47 @@
result.concretetype = lltype.Void
return [SpaceOperation("gc_pop_alive_pyobj", [var], result)]
+ # ----------------------------------------------------------------
+
+ def _deallocator_body_for_type(self, v, TYPE, depth=1):
+ if isinstance(TYPE, lltype.Array):
+
+ inner = list(self._deallocator_body_for_type('v_%i'%depth, TYPE.OF, depth+1))
+ if inner:
+ yield ' '*depth + 'i_%d = 0'%(depth,)
+ yield ' '*depth + 'l_%d = len(%s)'%(depth, v)
+ yield ' '*depth + 'while i_%d < l_%d:'%(depth, depth)
+ yield ' '*depth + ' v_%d = %s[i_%d]'%(depth, v, depth)
+ for line in inner:
+ yield line
+ yield ' '*depth + ' i_%d += 1'%(depth,)
+ elif isinstance(TYPE, lltype.Struct):
+ for name in TYPE._names:
+ inner = list(self._deallocator_body_for_type(
+ v + '_' + name, TYPE._flds[name], depth))
+ if inner:
+ yield ' '*depth + v + '_' + name + ' = ' + v + '.' + name
+ for line in inner:
+ yield line
+ elif isinstance(TYPE, lltype.Ptr):
+ yield ' '*depth + 'pop_alive(%s)'%v
+
+ def deallocation_graph_for_type(self, translator, TYPE, var):
+ def compute_ll_ops(hop):
+ hop.llops.extend(self.pop_alive(hop.args_v[1]))
+ return hop.inputconst(hop.r_result.lowleveltype, hop.s_result.const)
+ def pop_alive(var):
+ pass
+ pop_alive.compute_ll_ops = compute_ll_ops
+ pop_alive.llresult = lltype.Void
+
+ body = '\n'.join(self._deallocator_body_for_type('v', TYPE))
+ if not body:
+ return
+ src = 'def deallocator(v):\n' + body
+ d = {'pop_alive':pop_alive}
+ exec src in d
+ this = d['deallocator']
+ g = translator.rtyper.annotate_helper(this, [lltype.Ptr(TYPE)])
+ translator.rtyper.specialize_more_blocks()
+ return g
Modified: pypy/dist/pypy/rpython/memory/test/test_gctransform.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/test/test_gctransform.py (original)
+++ pypy/dist/pypy/rpython/memory/test/test_gctransform.py Sun Jan 29 19:47:15 2006
@@ -240,3 +240,40 @@
return 0
return 1
t = rtype_and_transform(f, [], gctransform.GCTransformer)
+
+# ----------------------------------------------------------------------
+
+def make_deallocator(TYPE, view=False):
+ def f():
+ pass
+ t = TranslationContext()
+ t.buildannotator().build_types(f, [])
+ t.buildrtyper().specialize(t)
+
+ transformer = gctransform.GCTransformer()
+ v = Variable()
+ v.concretetype = TYPE
+ graph = transformer.deallocation_graph_for_type(t, TYPE, v)
+ if view:
+ t.view()
+ return graph
+
+def dont_test_deallocator_simple():
+ S = lltype.GcStruct("S", ('x', lltype.Signed))
+ dgraph = make_deallocator(S)
+ assert dgraph is None
+
+def test_deallocator_less_simple():
+ TPtr = lltype.Ptr(lltype.GcStruct("T", ('a', lltype.Signed)))
+ S = lltype.GcStruct(
+ "S",
+ ('x', lltype.Signed),
+ ('y', TPtr),
+ ('z', TPtr),
+ )
+ dgraph = make_deallocator(S)
+
+def test_deallocator_less_simple2():
+ S = lltype.GcArray(lltype.Ptr(lltype.GcStruct("S", ('x', lltype.Signed))))
+ dgraph = make_deallocator(S)
+
More information about the Pypy-commit
mailing list